永夜初晗凝碧天

本博客现已全部转移到新地址,欲获取更多精彩文章,请访问http://acshiryu.github.io/

导航

poj1050经典DP的二维形式

To the Max
Time Limit: 1000MS Memory Limit: 10000K
Total Submissions: 27900 Accepted: 14460

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 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 * 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
题目大意就是给出一个n×n的矩阵,要求在里面找一个子矩阵,使得子矩阵中的元素和是最大的,输出这个最大的元素和
例如对于题目中的矩阵
 0 -2 -7  0
 9  2 -6  2
-4  1 -4  1
-1  8  0 -2
则可以找到子矩阵
 9  2
-4  1
-1  8
其所有元素和为15 是最大的子矩阵
故输出为15
解决这题首先要会求
给n个数,问这n个数的最大子串和是多少?

这一道题就是把上面的问题拓展到了二维,但解决方法类似

枚举所有的行组合,将这些行压缩成一个数列,进行上述操作就可以了
例如对于矩阵
1 2 3 4
2 3 4 1
2 3 1 4
将第一行和第二行压缩结果为3 5 7 5
同理,将第二行第三行压缩结果为4 6 5 5
将一二三行压缩结果为5 8 8 9
想一想,如果三维呢?三维无非就压缩两次嘛……
刚开始时有个细节没注意到,WA了一次
http://www.cnblogs.com/ACShiryu
参考代码:
 1      1#include<iostream>
2 #include<cstdlib>
3 #include<cstdio>
4 #include<cstring>
5 #include<algorithm>
6 #include<cmath>
7 using namespace std;
8 int a[105][105];
9 int sum[105];
10 int dp[105];
11 int main()
12 {
13 int n ;
14 while ( cin >> n )
15 {
16 int i , j , k , t;
17 for ( i = 0 ; i < n ; i ++ )
18 for ( j = 0 ; j < n ; j ++ )
19 cin >> a[i][j] ;
20 int sumall = - (1 << 30 );
21 for ( i = 0 ; i < n ; i ++ )
22 {
23 int sumdp;
24 for ( t = i + 1 ; t <= n ; t ++ )
25 {
26 for ( j = 0 ; j < n ; j ++ )
27 {
28 int sumi = 0 ;
29 for ( k = i ; k < t ; k ++ )
30 {
31 sumi += a[k][j] ;
32 }
33 sum[j] = sumi ;
34 if ( j )
35 sumall = max ( sumall , sumdp = max ( sumdp + sum[j] , sum[j] ) ) ;
36 else
37 sumall = max ( sumall , sumdp = sum[j] ) ;
38 }
39 }
40 }
41 cout << sumall << endl ;
42 }
43 return 0 ;
44 }

posted on 2011-08-14 00:06  ACShiryu  阅读(723)  评论(0编辑  收藏  举报