1768:最大子矩陣(NOIP2014初賽最后一題)


1768:最大子矩陣

總時間限制:
1000ms
內存限制:
65536kB
描述
已知矩陣的大小定義為矩陣中所有元素的和。給定一個矩陣,你的任務是找到最大的非空(大小至少是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個整數……)給出矩陣中的N 2個整數,整數之間由空白字符分隔(空格或者空行)。已知矩陣中整數的范圍都在[-127, 127]。
輸出
輸出最大子矩陣的大小。
樣例輸入
4
0 -2 -7 0 9 2 -6 2
-4 1 -4  1 -1

8  0 -2
樣例輸出
15
來源
翻譯自 Greater New York 2001 的試題

分析:

先對每一行計算前綴和數組,用於方便地計算每一行指定段的元素之和。

然后枚舉子矩陣的起始列first、結束列last。然后在這個區域計算列數為last-first+1的所有子矩陣的最大和。(計算過程類似一維矩陣的最大子段和。)

 1 #include <stdio.h>
 2 const int SIZE = 100;
 3 int matrix[SIZE + 1][SIZE + 1];
 4 int rowsum[SIZE + 1][SIZE + 1]; //rowsum[i][j]記錄第 i 行前 j 個數的和
 5 int m, n, i, j, first, last, area, ans;
 6 int main()
 7 {
 8     scanf("%d",&n);
 9     m=n;
10     for (i = 1; i <= m; i++)
11         for (j = 1; j <= n; j++)
12             scanf("%d", &matrix[i][j]);
13     ans = matrix[1][1];
14     for (i = 1; i <= m; i++)
15         rowsum[i][0]=0;
16     for (i = 1; i <= m; i++)
17         for (j = 1; j <= n; j++)
18             rowsum[i][j] = rowsum[i][j-1]+matrix[i][j];
19     for (first = 1; first <= n; first++)
20         for (last = first; last <= n; last++) 
21         {
22             area=0;
23             for (i = 1; i <= m; i++) 
24             {
25                 area += rowsum[i][last] -rowsum[i][first-1];
26                 if (area > ans) ans = area;
27                 if (area < 0) area = 0;
28             }
29         }
30     printf("%d\n", ans);
31     return 0;
32 }

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM