Largest Submatrix
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 1589 Accepted Submission(s): 761
Problem Description
Now here is a matrix with letter ‘a‘,‘b‘,‘c‘,‘w‘,‘x‘,‘y‘,‘z‘ and you can change ‘w‘ to ‘a‘ or ‘b‘, change ‘x‘ to ‘b‘ or
‘c‘, change ‘y‘ to ‘a‘ or ‘c‘, and change ‘z‘ to ‘a‘, ‘b‘ or ‘c‘. After you changed it, what‘s the largest submatrix with
the same letters you can make?
Input
The input contains multiple test cases. Each test case begins with m and n (1 ≤ m, n ≤ 1000) on line. Then come the
elements of a matrix in row-major order on m lines each with n letters. The input ends once EOF is met.
Output
For each test case, output one line containing the number of elements of the largest submatrix of all same letters.
Sample Input
2 4
abcw
wxyz
Sample Output
3
Source
2009 Multi-University Training Contest 7 - Host by FZU
题目大意:有个字母矩阵,包含字母"a、b、c、w、x、y、z",其中,w能变为"a、b",
x能变为"b、c",y能变为"a、c",z能变为"a、b、c"。问能构成的最大字母完全一样的子
矩阵面积为多大?
思路:和HDU1505、HDU1506一样的思路,其中a[i][j]表示转换为字母a后以第i行为底,
第j列上方连续空闲位置的高度。b[i][j]表示字母b……,c[i][j]表示字母c……
遍历计算出该点向左右两边延伸的左右边界,从而计算出面积,最终比较计算出最大面积。
参考博文:HDU1505http://blog.csdn.net/lianai911/article/details/40302489
HDU1506http://blog.csdn.net/lianai911/article/details/40208265
#include<stdio.h> #include<string.h> #include<algorithm> using namespace std; int a[1100][1100],b[1100][1100],c[1100][1100],l[1100],r[1100]; int main() { int M,N; char ch; while(~scanf("%d%d",&M,&N)) { for(int i = 1; i <= M; i++) { getchar(); for(int j = 1; j <= N; j++) { scanf("%c",&ch); if(ch=='a' || ch=='w' || ch=='y' || ch=='z') a[i][j] = a[i-1][j] + 1; else a[i][j] = 0; if(ch=='b' || ch=='w' || ch=='x' || ch=='z') b[i][j] = b[i-1][j] + 1; else b[i][j] = 0; if(ch=='c' || ch=='x' || ch=='y' || ch=='z') c[i][j] = c[i-1][j] + 1; else c[i][j] = 0; } } int area = -0xffffff0; for(int i = 1; i <= M; i++) { // ------------------求a最大面积--------------- l[0] = 1,r[N+1] = N; a[i][0] = a[i][N+1] = -1; for(int j = 1; j <= N; j++) { l[j] = j; while(a[i][l[j]-1] >= a[i][j]) l[j] = l[l[j]-1]; } for(int j = N; j >= 1; j--) { r[j] = j; while(a[i][r[j]+1] >= a[i][j]) r[j] = r[r[j]+1]; } for(int j = 1; j <= N; j++) { if(a[i][j] * (r[j]-l[j]+1) > area) area = a[i][j] * (r[j]-l[j]+1); } // ----------------求b最大面积---------------- l[0] = 1,r[N+1] = N; b[i][0] = b[i][N+1] = -1; for(int j = 1; j <= N; j++) { l[j] = j; while(b[i][l[j]-1] >= b[i][j]) l[j] = l[l[j]-1]; } for(int j = N; j >= 1; j--) { r[j] = j; while(b[i][r[j]+1] >= b[i][j]) r[j] = r[r[j]+1]; } for(int j = 1; j <= N; j++) { if(b[i][j] * (r[j]-l[j]+1) > area) area = b[i][j] * (r[j]-l[j]+1); } // -------------求c最大面积--------------- l[0] = 1,r[N+1] = N; c[i][0] = c[i][N+1] = -1; for(int j = 1; j <= N; j++) { l[j] = j; while(c[i][l[j]-1] >= c[i][j]) l[j] = l[l[j]-1]; } for(int j = N; j >= 1; j--) { r[j] = j; while(c[i][r[j]+1] >= c[i][j]) r[j] = r[r[j]+1]; } for(int j = 1; j <= N; j++) { if(c[i][j] * (r[j]-l[j]+1) > area) area = c[i][j] * (r[j]-l[j]+1); } } printf("%d\n",area); } return 0; }