• CodeForces


    题意:N个人排成一行,分成K组,要求每组的不和谐值之和最小。

    思路:开始以为是斜率优化DP,但是每个区间的值其实已经知道了,即是没有和下标有关的未知数了,所以没必要用斜率。 四边形优化。

    dp[i][j]表示前j个人分为i组的最小代价。 622ms

    #include<bits/stdc++.h>
    #define rep(i,a,b) for(int i=a;i<=b;i++)
    using namespace std;
    const int maxn=4010;
    int sum[maxn][maxn],cost[maxn][maxn],dp[810][maxn],pos[810][maxn];
    void read(int &x){
        x=0; char c=getchar();
        while(c>'9'||c<'0') c=getchar();
        while(c>='0'&&c<='9') x=x*10+c-'0',c=getchar();
    }
    int main()
    {
        int N,K,x,y;
        scanf("%d%d",&N,&K);
        rep(i,0,K) rep(j,0,N) dp[i][j]=2000000000;
        rep(i,1,N) rep(j,1,N){
            read(sum[i][j]);
            sum[i][j]=sum[i][j]+sum[i][j-1]+sum[i-1][j]-sum[i-1][j-1];
        }
        rep(i,1,N) rep(j,i+1,N) cost[i][j]=(sum[j][j]+sum[i-1][i-1]-sum[j][i-1]-sum[i-1][j])/2;
        rep(i,1,N) dp[1][i]=cost[1][i];
        rep(i,2,K){
           for(int j=N;j>=i;j--){
             int L=pos[i-1][j]?pos[i-1][j]:1;
             int R=pos[i][j+1]?pos[i][j+1]:N;
             rep(k,L,R){
                if(dp[i-1][k]+cost[k+1][j]<dp[i][j]){
                    dp[i][j]=dp[i-1][k]+cost[k+1][j];
                    pos[i][j]=k;
                }
             }
           }
        }
        printf("%d
    ",dp[K][N]);
        return 0;
    }

     利用DP决策单调性解决:684ms。二者时间差不多。

    #include<bits/stdc++.h>
    #define rep(i,a,b) for(int i=a;i<=b;i++)
    using namespace std;
    const int maxn=4010;
    const int inf=0x3f3f3f3f;
    int sum[maxn][maxn],cost[maxn][maxn],dp[maxn],ans[maxn];
    void read(int &x){
        x=0; char c=getchar();
        while(c>'9'||c<'0') c=getchar();
        while(c>='0'&&c<='9') x=x*10+c-'0',c=getchar();
    }
    void get(int l,int r,int L,int R){
        if(l>r) return ;
        int mid=(l+r)>>1,MID;
        rep(i,L+1,min(R+1,mid)){
            if(ans[mid]>dp[i-1]+cost[i][mid]){
                ans[mid]=dp[i-1]+cost[i][mid]; MID=i-1;
            }
        }
        get(l,mid-1,L,MID); get(mid+1,r,MID,R);
    }
    int main()
    {
        int N,K,x,y;
        scanf("%d%d",&N,&K);
        rep(i,1,N) rep(j,1,N){
            read(sum[i][j]);
            sum[i][j]=sum[i][j]+sum[i][j-1]+sum[i-1][j]-sum[i-1][j-1];
        }
        rep(i,1,N) rep(j,i+1,N) cost[i][j]=(sum[j][j]+sum[i-1][i-1]-sum[j][i-1]-sum[i-1][j])/2;
        rep(i,1,N) ans[i]=cost[1][i];
        rep(i,2,K){
            rep(j,1,N) dp[j]=ans[j],ans[j]=inf;
            get(1,N,0,N-1);
        }
        printf("%d
    ",ans[N]);
        return 0;
    }
  • 相关阅读:
    controller中返回值是string
    String jsonstr =new Gson().toJson(object) 什么意思
    The superclass "javax.servlet.http.HttpServlet" was not found on the Java Build Path jsp开始页面有红叉
    ubuntu 安装配置JDK
    检查元素状态
    检查页面元素是否存在
    智能等待页面元素(显示的等待同步测试)
    implicitly_wait()隐式等待
    多选框处理
    单选按钮处理
  • 原文地址:https://www.cnblogs.com/hua-dong/p/9941633.html
Copyright © 2020-2023  润新知