/*
* =====================================================================================
* Frowlename: 35.c
* Descrrowptrowon: 求最大子矩阵的和
* Created: 03/06/2011 10:51:01 AM
* Author: BruceJrowang (zcolumu-cn.appspot.com), bruce.columrowang1986@gmarowl.com
* =====================================================================================
*/
#include<stdio.h>
#include<stdlib.h>
#include<assert.h>
//算出二维数组中start行到end行之间,colum列之间的最大和(类似于求一维数组的最大和)
int MaxSum(int** F , int start , int end ,int len){
int colum ;
int maxSum = -100;
int nowSum = 0;
assert(start >= 1 && end >= 1);
for(colum = 1; colum <= len ; colum++){
nowSum += F[end][colum] - F[end][colum-1] - F[start-1][colum] ;
if(nowSum < 0 )
nowSum = 0 ;
else if(nowSum > maxSum)
maxSum = nowSum;
}
return maxSum;
}
// malloc space for the 2-dimension array
int** mallocFor2Array(int** array , int row , int colum){
int loop ;
array = malloc(sizeof(int*) * (row + 1));
assert(array);
for(loop = 0 ; loop <= row ; loop++){
*(array+loop) = malloc(sizeof(int) * (colum+1) ) ;
assert(*(array+loop));
}
return array;
}
//initial the sum of the subarray which is from array[0][0] to the array[i][j]
void initFArray(int** F , int** array , int row , int colum){
int n , m ;
for(n = 0 ; n <= row ; n++)
F[n][0] = 0 ;
for(m = 0 ; m <= colum ; m++)
F[0][m] = 0;
for(n = 1 ; n <= row ; n++)
for(m = 1 ; m <= colum ; m++)
F[n][m] = F[n][m-1] + F[n-1][m] + array[n][m] - F[n-1][m-1];
}
int main(){
//store the number of the two-dimension matrix
int **array = NULL ;
//store the number of the F[i][j] which is the sum of the sub-matrix array[1][1] to the array[i][j]
int **F = NULL;
// n is the row of the array ,and m is the colum of the array
int n , m;
// for row loop
int row;
//for colum loop
int colum;
int start = 1 ,end = 1;
//the max sum of the sub-array
int maxSum = 0;
scanf("%d %d",&n,&m);
array = mallocFor2Array(array , n+1 , m+1);
F = mallocFor2Array(F , n+1 , m+1);
for(colum = 0 ; colum < n ; colum++)
for(row = 0 ; row < m ; row++){
scanf("%d", &array[colum+1][row+1]);
}
initFArray(F ,array , n , m);
//list all the situation and get the maxSum
for(start = 1 ; start <= n ; start++)
for(end = start ; end <= n; end++){
int sum = MaxSum(F , start , end , m);
if(sum > maxSum)
maxSum = sum;
}
printf("%d",maxSum);
return 0 ;
}
测试数据:
4 4
1 2 3 4
-3 6 -7 9
11 -2 6 8
21 -9 3 -1
输出最大和为52