#include <iostream>
#include <string>
#include <assert.h>
#include <malloc.h>
#include <iostream>
#include <stdlib.h>
#include <memory.h>
#include <time.h>
#include <limits.h>
using namespace std;
//动态分配rows行、cols列的二维数组
template<typename T>
bool allocateMemory2D(T ***p, const int rows, const int cols)
{
*p = NULL;
*p = (T **)malloc(rows * sizeof(T *));
if (*p == NULL) return false;
memset(*p, 0, sizeof(T *)* rows);
for (int i = 0; i < rows; i++)
{
(*p)[i] = (T *)malloc(cols * sizeof(T));
if ((*p)[i] == NULL) return false;
}
return true;
}
//释放二维动态数组的空间
template<typename T>
void freeMemory2D(T ***p, const int rows)
{
if (*p != NULL)
{
for (int i = 0; i < rows; i++)
{
if ((*p)[i] != NULL)
{
free((*p)[i]);
(*p)[i] = NULL;
}
}
free(*p);
*p = NULL;
}
}
//用随机数填充二维数组(矩阵)
template<typename T, typename V>
bool generateNNumbers2D(T **a, int rows, int cols, V minValue, V maxValue)
{
//assert(a != NULL && rows > 0 && cols > 0);
if (a == NULL || rows < 1 && cols < 1) return false;
if (minValue > maxValue) swap(minValue, maxValue);
const int N = 999999;
srand((unsigned)time(NULL));
for (int i = 0; i < rows; i++)
{
for (int j = 0; j < cols; j++)
{
a[i][j] = rand() % (int)(maxValue - minValue + 1) + minValue + rand() % (N + 1) / (float)(N + 1);
}
}
return true;
}
template<typename T>
void displayArray2D(T **a, const int rows, const int cols)
{
assert(a != NULL && rows > 0 && cols > 0);
for (int i = 0; i < rows; i++)
{
printf("%d: ", i + 1);
for (int j = 0; j < cols; j++)
{
if (sizeof(T) == 1) cout << (int)a[i][j] << " ";
else cout << a[i][j] << " ";
}
cout << endl;
}
}
template<typename T>
void displayMaxSubMatrix2D(T **mat, int leftTopRow, int leftTopCol, int rightBottomRow, int rightBottomCol)
{
int row, col;
for (row = leftTopRow; row <= rightBottomRow; row++)
{
for (col = leftTopCol; col <= rightBottomCol; col++)
{
if (sizeof(T) == 1) cout << (int)mat[row][col] << " ";
else cout << mat[row][col] << " ";
}
cout << endl;
}
}
//求最大子矩阵,即该子矩阵的所有元素之和是所有子矩阵中最大的
void main(void)
{
int ROW, COL;
char **mat = NULL; //可以改成其他类型,如int **mat; float **mat; char **mat;
long double max, sum;
int i, j, m, n, row, col;
int leftTopRow, leftTopCol, rightBottomRow, rightBottomCol;
bool isDataAutoGenerate;
char ch;
char buf[256];
cout << "自动生成矩阵吗(y/Y:是):";
cin >> ch;
isDataAutoGenerate = (ch == 'y' || ch == 'Y');
//清空输入缓冲区,如果你输入的东西很长,缓冲区依然残留数据,导致cin >> order
//得到脏数据,程序的行为可能就不是你所预期的了。
cin.getline(buf, sizeof(buf));
//这里默认矩阵行列相同,当然你可以改成行列可以取任意值的情况
cout << "请输入矩阵的行数和列数:";
while (cin >> ROW && cin >> COL)
{
if (ROW < 1 || COL < 1)
{
cout << "矩阵的行数和列数均不能小于1哦." << endl;
break;
}
/*mat = new int*[ROW];
memset(mat, 0, sizeof(*mat) * ROW);
for (i = 0; i < ROW; i++) mat[i] = new int[COL];*/
allocateMemory2D(&mat, ROW, COL);
if (isDataAutoGenerate)
{
generateNNumbers2D(mat, ROW, COL, -100, 100);
cout << "自动生成的" << ROW << "行," <<COL << "列矩阵为:" << endl;
displayArray2D(mat, ROW, COL);
}
else
{
cout << "依次输入矩阵的每一个元素:\n";
/*for (i = 0; i < ROW * COL; i++) cin >> mat[i / ROW][i % COL];*/
for (i = 0; i < ROW; i++)
for (j = 0; j < COL; j++)
cin >> mat[i][j];
}
max = LONG_MIN;
sum = 0;
for (i = 1; i <= ROW; i++)
{
for (j = 1; j <= COL; j++)
{
for (m = 0; m <= ROW - i; m++)
{
for (n = 0; n <= COL - j; n++)
{
sum = 0;
for (row = m; row < m + i; row++)
{
for (col = n; col < n + j; col++)
{
sum += mat[row][col];
}
}
if (sum > max)
{
leftTopRow = m;
leftTopCol = n;
rightBottomRow = row - 1;
rightBottomCol = col - 1;
max = sum;
}
}
}
}
}
/*for (i = 0; i < ROW; i++) if (mat[i]) delete mat[i];
if (mat) delete[] mat;*/
cout << "连续的最大子矩阵和为:" << max << endl;
cout << "(" << leftTopRow << ", " << leftTopCol << "), " \
<< "(" << rightBottomRow << ", " << rightBottomCol << ")" << endl;
cout << "连续的最大子矩阵为:" << endl;
displayMaxSubMatrix2D(mat, leftTopRow, leftTopCol, rightBottomRow, rightBottomCol);
cout << endl;
freeMemory2D(&mat, ROW);
cout << "请输入矩阵的行数和列数:";
}
}