[Jobdu] 题目1139:最大子矩阵

题目描述:

已知矩阵的大小定义为矩阵中所有元素的和。给定一个矩阵,你的任务是找到最大的非空(大小至少是1 * 1)子矩阵。
比如,如下4 * 4的矩阵

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

的最大子矩阵是

9 2
-4 1
-1 8

这个子矩阵的大小是15。

输入:

输入是一个N * N的矩阵。输入的第一行给出N (0 < N <= 100)。
再后面的若干行中,依次(首先从左到右给出第一行的N个整数,再从左到右给出第二行的N个整数……)给出矩阵中的N2个整数,整数之间由空白字符分隔(空格或者空行)。
已知矩阵中整数的范围都在[-127, 127]。

输出:

测试数据可能有多组,对于每组测试数据,输出最大子矩阵的大小。

样例输入:
4

0 -2 -7 0

9 2 -6 2

-4 1 -4  1

-1 8  0 -2
样例输出:
15

第一映像是暴力枚举,不过显然会超时,然后就想到了DP。其实因为矩阵肯定是对齐的,所以如我们将两行加起来求最大子数组就可以得到一个行数为2的子矩阵。所以问题就转化成了求一个数组的最大子数组和。然后就是枚举第i行到第j行相加得到的数组了。注意res的值不能设为0,因为可能最后的结果是负数。

 1 #include <iostream>

 2 #include <cstdio>

 3 #include <cstring>

 4 using namespace std;

 5  

 6 int N;

 7 int a[101][101];

 8 int dp[101];

 9  

10 int getMaxArray(int a[], int N) {

11     int max = a[0], tmp = 0;

12     for (int i = 0; i < N; ++i) {

13         if (tmp > 0) {

14             tmp += a[i];

15         } else {

16             tmp = a[i];

17         }

18         max = max > tmp ? max : tmp;

19     }

20     return max;

21 }

22  

23 int main() {

24     //freopen("input.txt", "r", stdin);

25     while (scanf("%d", &N) != EOF) {

26         for (int i = 0; i < N; ++i) {

27             for (int j = 0; j < N; ++j) {

28                 scanf("%d", &a[i][j]);

29             }

30         }

31         int res = a[0][0], tmp;

32         for (int i = 0; i < N; ++i) {

33             memset(dp, 0, sizeof(dp));

34             for (int j = i; j < N; ++j) {

35                 for (int k = 0; k < N; ++k) {

36                     dp[k] += a[j][k];

37                 }

38                 tmp = getMaxArray(dp, N);

39                 res = res > tmp ? res : tmp;

40             }

41         }

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

43     }

44     return 0;

45 }

46  

47 /**************************************************************

48     Problem: 1139

49     User: hupo250

50     Language: C++

51     Result: Accepted

52     Time:60 ms

53     Memory:1560 kb

54 ****************************************************************/

 

你可能感兴趣的:(job)