noi 1768 最大子矩阵

题目链接:http://noi.openjudge.cn/ch0206/1768/

可能是数据修改了吧,O(n6)过不了了。

主要是在求一个矩阵的和时,重复计算了很多次。

矩阵首先压缩一下。在输入的时候,就计算好每一列的和于a[i][j]中。

dp:

枚举上界(第一重循环),枚举下界(第二重循环),枚举列数(第三重循环),总的时间复杂度为O(n3);

怎么得到这一列的和呢? 就是利用预处理的 a 数组。temp= a[j][k] - a[i-1][k];

然后这一列上的 dp 方程 f[k] = max(f[k-1]+temp,temp);  //选还是不选这一列;

temp2 = max(f[k]) 是这一列的最优值。循环完后,就是 ans = max(temp2) 只一个区间的最优值了。

/*
#include<iostream>
using namespace std;

#define INF 0x3f3f3f3f

const int Maxn = 110;
int a[Maxn][Maxn];

int main()
{
    int n;
    cin>>n;
    for(int i=1; i<=n; i++)
        for(int j=1; j<=n; j++)
            cin>>a[i][j];

    int ans = -INF;
    int sum = 0;
    for(int i=1; i<=n; i++)
    {
        for(int j=1; j<=n; j++)
        {
            for(int r=i; r<=n; r++)
            {
                for(int c=j; c<=n; c++)
                {
                    sum = 0;
                    for(int k=i;k<=r;k++) {
                        for(int t=j;t<=c;t++) {
                            sum +=a[k][t];
                        }
                    }
                    if(sum>ans)
                        ans = sum;
                }
            }
        }
    }

    cout<<ans<<endl;


    return 0;
}
*/


#include <bits/stdc++.h>
using namespace std;

const int INF = 0x3f3f3f3f;
const int Maxn = 110;
int a[Maxn][Maxn];
int f[Maxn];
int n;

int main()
{
    int ans = -INF;

    scanf("%d",&n);
    for(int i=1; i<=n; i++)
        for(int j=1; j<=n; j++)
        {
            scanf("%d",&a[i][j]);
            a[i][j] +=a[i-1][j];
        }

    for(int i=1; i<=n; i++)
    {
        for(int j=i; j<=n; j++)
        {
            memset(f,0,sizeof(f));
            int temp1 = -INF;
            for(int k=1; k<=n; k++)
            {
                int temp2 = a[j][k] - a[i-1][k];
                f[k] = max(f[k-1]+temp2,temp2);
                temp1 = max(temp1,f[k]);
            }
            ans = max(ans,temp1);
        }
    }

    printf("%d\n",ans);



    return 0;
}

 

转载于:https://www.cnblogs.com/TreeDream/p/6028227.html

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值