bzoj 1084 //1084: [SCOI2005]最大子矩阵 动态规划

bzoj 1084   //1084: [SCOI2005]最大子矩阵   //在线测评地址https://www.lydsy.com/JudgeOnline/problem.php?id=1084

更多题解,详见https://blog.csdn.net/mrcrack/article/details/90228694BZOJ刷题记录

Accepted1320 kb116 msC++/Edit1261 B

//1084: [SCOI2005]最大子矩阵
//在线测评地址https://www.lydsy.com/JudgeOnline/problem.php?id=1084
//
//因题中"分值",一直阻塞,要是改成"数值",就没什么问题了。
/*
样例解释如下
1
2

3 3
*/
//矩阵和,采用动归,能很快求出
//难在,如何挑选   子矩阵。2019-11-5
//此文https://www.cnblogs.com/shenben/p/5924518.html思路,代码都很棒。2019-11-5
/*

*/

//样例通过,提交Wrong_Answer    1512 kb    52 ms    C++/Edit    1260 B。2019-11-5
//排查,发现
//if(i==j)for(l=0;l<i;l++)f[i][j][k]=max(f[i][j][k],f[l][l][k-1]+s1[i]-s1[l]+s2[j]-s2[l]);//此处错写成if(i==j)for(l=0;l<i;l++)f[i][j][k]=max(f[i][j][k],f[l][l][k]+s1[i]-s1[l]+s2[j]-s2[l]);
//样例通过,提交AC.2019-11-5   动归似乎有点感觉。
#include <stdio.h>
#include <string.h>
#define maxn 103
#define maxk 11
int dp[maxn][maxn],f[maxn][maxn][maxk],s1[maxn],s2[maxn],N,M,K;
int max(int a,int b){
    return a>b?a:b;
}
int main(){
    int i,j,k,x,l,y;
    scanf("%d%d%d",&N,&M,&K);
    if(M==1){
        s1[0]=0,memset(dp,0,sizeof(dp));
        for(i=1;i<=N;i++)scanf("%d",&x),s1[i]=s1[i-1]+x;//s1[]前缀和
        for(k=1;k<=K;k++)
            for(i=1;i<=N;i++){
                dp[i][k]=dp[i-1][k];
                for(l=0;l<i;l++)dp[i][k]=max(dp[i][k],dp[l][k-1]+s1[i]-s1[l]);
            }
        printf("%d\n",dp[N][K]);
    }else if(M==2){
        s1[0]=s2[0]=0,memset(f,0,sizeof(f));
        for(i=1;i<=N;i++)scanf("%d%d",&x,&y),s1[i]=s1[i-1]+x,s2[i]=s2[i-1]+y;//读取技巧,值得一学
        for(k=1;k<=K;k++)
            for(i=1;i<=N;i++)
                for(j=1;j<=N;j++){
                    f[i][j][k]=max(f[i-1][j][k],f[i][j-1][k]);
                    for(l=0;l<i;l++)f[i][j][k]=max(f[i][j][k],f[l][j][k-1]+s1[i]-s1[l]);
                    for(l=0;l<j;l++)f[i][j][k]=max(f[i][j][k],f[i][l][k-1]+s2[j]-s2[l]);
                    if(i==j)for(l=0;l<i;l++)f[i][j][k]=max(f[i][j][k],f[l][l][k-1]+s1[i]-s1[l]+s2[j]-s2[l]);//此处错写成if(i==j)for(l=0;l<i;l++)f[i][j][k]=max(f[i][j][k],f[l][l][k]+s1[i]-s1[l]+s2[j]-s2[l]);
                }
        printf("%d\n",f[N][N][K]);
    }
    return 0;
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值