poj 1081 To The Max

To The Max

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)
Total Submission(s): 12697    Accepted Submission(s):
6090

Problem Description

Given a two-dimensional array of positive and negative
integers, a sub-rectangle is any contiguous sub-array of size 1 x 1 or greater
located within the whole array. The sum of a rectangle is the sum of all the
elements in that rectangle. In this problem the sub-rectangle with the largest
sum is referred to as the maximal sub-rectangle.

As an example, the
maximal sub-rectangle of the array:

0 -2 -7 0
9 2 -6 2
-4 1 -4
1
-1 8 0 -2

is in the lower left corner:

9 2
-4 1
-1
8

and has a sum of 15.

Input

The input consists of an N x N array of integers. The
input begins with a single positive integer N on a line by itself, indicating
the size of the square two-dimensional array. This is followed by N 2 integers
separated by whitespace (spaces and newlines). These are the N 2 integers of the
array, presented in row-major order. That is, all numbers in the first row, left
to right, then all numbers in the second row, left to right, etc. N may be as
large as 100. The numbers in the array will be in the range
[-127,127].

Output

Output the sum of the maximal sub-rectangle.

Sample Input

4
0 -2 -7 0 9 2 -6 2
-4 1 -4 1 -1
8 0 -2

Sample Output

15

题意:二维的矩阵,从中找到一个子矩阵,使得子矩阵的和最大。

思路:可以先考虑一维的情况,一维时即数列,求数列中连续子列的和的最大值,做法就是在线处理,从头到尾一个一个元素考虑并累加过去,记当前累加值为sum,若累加的时候当前sum值小于0了,那么舍弃前面的累加列,sum更新为0,并且从下一个位置

的元素重新开始累加,途中不断的更新sum,找出最大的sum值即可,二维的情况可以看作一维的延伸情况,如果把列固定住(即选取矩阵连续的几列并固定,先算好每一行的这几列的和值),此时纵向的从上到下累加就可以看成是一维情况下的累加,算法类同。

AC代码:

#define _CRT_SECURE_NO_DEPRECATE
#include<iostream>
#include<algorithm>
#include<string>
#include<set>
#include<map>
#include<vector>
#include<queue>
#include<functional>
using namespace std;
const int N_MAX= 100+2;
int a[N_MAX][N_MAX];
int sum[N_MAX][N_MAX];
int main() {
    int n;
    while (scanf("%d", &n) != EOF) {
        memset(sum,0,sizeof(sum));
        memset(a, 0,sizeof(a));
        for (int i = 0; i < n; i++) {
            for (int j = 1; j <= n; j++) {
                scanf("%d", &a[i][j]);
            }
        }
        for (int i = 0; i < n; i++) {
            for (int j = 1; j <= n; j++) {
                 sum[i][j] =sum[i][j-1]+ a[i][j];
            }
        }

        int res = -INT_MAX;
        for (int i = 0; i < n; i++) {//固定i,j
            for (int j = i+1; j <= n; j++) {
                int S = 0;
                for (int k = 0; k < n; k++) {
                    S += sum[k][j]-sum[k][i-1];//累加上闭区间[i,j]值的和
                    if (S > res)
                        res = S;
                    if (S < 0)S = 0;

                }
            }
        }
        printf("%d\n",res);

    }
return 0;
}

思路

时间: 2024-12-14 18:46:29

poj 1081 To The Max的相关文章

hdu 1081 &amp; poj 1050 To The Max(最大和的子矩阵)

转载请注明出处:http://blog.csdn.net/u012860063 Description Given a two-dimensional array of positive and negative integers, a sub-rectangle is any contiguous sub-array of size 1*1 or greater located within the whole array. The sum of a rectangle is the sum

hdu 1081 To The Max(dp+化二维为一维)

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1081 To The Max Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 8839    Accepted Submission(s): 4281 Problem Description Given a two-dimensional ar

POJ 1050 To the Max DP题解

一维最大字段和的扩展. 要诀是固定列的左右点,比如左边记录为left, 右边记录为right,那么一个循环left从0到COL,行最大值,那么right从left开始循环到COl,就可以考虑到所有列组合了,这个循环是O(n*n),然后求范围列内的行最大子段和,时间是O(n), 这样巧妙地把二维的问题转化为一维了,最终时间复杂度是O(n^3). 可以参考Geeks上的讲解,不过他的最大子段和代码写的挺挫的,我的代码会简洁很多,而且也考虑到了负值情况了. Geeks地址:http://www.gee

HDU 1081 To The Max(DP)

题意  求一个n*n矩阵的最大子矩阵和 HDU 1003 max sum 的升级版   把二维简化为一维就可以用1003的方法去做了  用mat[i][j]存  第i行前j个数的和   那么mat[k][j]-mat[k][i]就表示第k行  第i+1个数到第j个数的和了   再将k从一枚举到n就可以得到这个这个宽度为j-i的最大矩阵和了   然后i,j又分别从1枚举到n就能得到结果了   和1003的方法一样  只是多了两层循环 #include<cstdio> #include<cs

hdu 1081 &amp;amp; poj 1050 To The Max(最大和的子矩阵)

转载请注明出处:http://blog.csdn.net/u012860063 Description Given a two-dimensional array of positive and negative integers, a sub-rectangle is any contiguous sub-array of size 1*1 or greater located within the whole array. The sum of a rectangle is the sum

HDU 1081 To The Max 暴力模拟O(n^4) dp优化O(n^3)

原题: http://acm.hdu.edu.cn/showproblem.php?pid=1081 题目大意: 求给定边长的正方形选一个矩形,使它包含的所有元素的值最大. 大家都知道(a+b)^2的展开式,这里的优化就是用了这个原理来做的优化,我们的dp值是我们前i行j列的矩形区域的值. 任意矩形区域的值通过该展开式也能求解,所以我们可以暴力枚举每种以左上角(k,l)到右下角(i,j)的情况. 对于这个题边长是100,4层循环是10^8,因为循环并跑不了这么多,刚好也能卡过去. 代码如下: #

HDU - 1003 - Max Sum &amp;&amp; POJ - 1050 - To the Max (经典DP问题)

题目传送:HDU - 1003 思路:最大子序列和 dp[i]= a[i]   (dp[i-1]<0) dp[i]= dp[i-1]+a[i]   (dp[i-1]>=0) AC代码: #include <cstdio> #include <cstring> #include <iostream> #include <algorithm> #include <cmath> #include <queue> #include

poj - 1050 - To the Max(dp)

题意:一个N * N的矩阵,求子矩阵的最大和(N <= 100, -127 <= 矩阵元素 <= 127). 题目链接:http://poj.org/problem?id=1050 -->>将二维压缩为一维,对一维进行dp求解. 将二维压缩成一维: 1.第1行 2.第2行加第1行 3.第3行加第2行加第1行 -- N.第N行加第N-1行加--加第1行 1.第2行 2.第3行加第2行 -- 1.第N行 对于一维情况,设dp[i]表示以第i个元素结尾的最大连续和,则状态转移方程为

POJ 1050 To the Max(DP,最大子矩阵和)

POJ 1050 题意:给一个矩阵,求出元素和最大的子矩阵. 思路: 之前曾写过最大子串和的一篇文章,这次由一维上升到了二维. 我们可以通过累加每行相同列或每列相同行的值,将其储存在一个数组中,便可以将二维降至一维. 时间复杂度为O(n^3). 参考: 累加每一行相同列的做法(java实现) 累加每一列相同行的做法(C++实现) code: /* *Author : Flint_x *Created Time : 2015-07-23 15:10:01 *File name : POJ1050.