zoukankan      html  css  js  c++  java
  • CF1101F Trucks and Cities

    Solution

    (f[i][j][k]) 表示一辆每公里耗油量为 (1) 的货车从 (i)(j) 中途加 (k) 次油最小的油箱容量。枚举起点 (st) 和加油的次数 (k) ,这样就固定了两维,显然有DP方程:

    [f[i][j][k]=minlimits_{ileq pleq j}(max(f[i][p][k-1],a[j]-a[p])) ]

    这是 (O(n^4)) 的,但是我们发现 (p) 增加的时候, (f[i][p][k-1]) 是单增的, (a[j]-a[p]) 是单减的,所以可以找出区间的决策点,即对整个区间进行分治。

    然后复杂度就变成了 (O(n^3))

    代码

    #include<iostream>
    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #define ll long long
    
    using namespace std;
    const int N=405;
    int n,m,a[N],f[N][N][N];//f[i][j][k]代表i到j分成k+1段
    
    inline int read(){
        int x=0,f=1;
        char ch=getchar();
        while(!isdigit(ch)){if(ch=='-') f=-1;ch=getchar();}
        while(isdigit(ch)){x=x*10+(ch^48);ch=getchar();}
        return x*f;
    }
    
    void solve(int st,int k,int l,int r,int ql,int qr){
        if(l>r) return ;
        int mid=(l+r)>>1,opt=0,temp=0;
        for(int i=ql;i<=min(qr,mid);i++)
            if(!opt||max(a[mid]-a[i],f[st][i][k-1])<temp)
                temp=max(a[mid]-a[i],f[st][i][k-1]),opt=i;
        f[st][mid][k]=temp;
        solve(st,k,l,mid-1,ql,opt);
        solve(st,k,mid+1,r,opt,qr);
    }
    
    int main(){
        n=read();m=read();
        for(int i=1;i<=n;i++)
            a[i]=read();
        for(int i=1;i<=n;i++)
            for(int j=i;j<=n;j++) f[i][j][0]=a[j]-a[i];
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)
                solve(i,j,i+1,n,i+1,n);
        ll ans=0;
        for(int i=1;i<=m;i++){
            int s=read(),t=read(),c=read(),r=read();
            ans=max(ans,1ll*f[s][t][r]*c);
        }
        printf("%lld
    ",ans);
        return 0;
    }
    
  • 相关阅读:
    【4】通过简化的正则表达式处理字符串
    水晶报表WEB方式下不打印的问题
    字符串处理总结(旧)
    【3】利用Word模板生成文档的总结
    这个教授的观点颇犀利
    互联网时代还需要看书吗?
    怎样更爽地看PDF杂志
    吐槽win7
    信息技术真有想象的那么靠谱吗?
    无线路由器桥接的设置
  • 原文地址:https://www.cnblogs.com/jasony/p/13641440.html
Copyright © 2011-2022 走看看