題目:
求一個矩陣中最大的二維矩陣(元素和最大).如:
1 2 0 3 4
2 3 4 5 1
1 1 5 3 0
中最大的二維矩陣是:
4 5
5 3
要求:(1)寫出算法;(2)分析時間複雜度;(3)用C 寫出關鍵代碼.
思路一:
這個題目要求出最大的二維矩陣,我們首先想到的一個解法就是:從行1到行N進行遍歷,以二維矩陣爲單元進行遍歷,也就說(行x列x -- 行x+1列x+1)爲一個單位進行遍歷,遍歷的過程中記錄該矩陣的和值,並和最大和值進行比較,保存最大的二維矩陣和值所對應的行列值,直到遍歷結束就可以找到最大的二維矩陣。O(NLine*NCol),其中NLine代表的是該矩陣的行數,NCol代表的該矩陣的列數。
代碼如下:
/*-----------------------------
Copyright by yuucyf. 2011.08.25
------------------------------*/
#include "stdafx.h"
#include <assert.h>
#include <iostream>
using namespace std;
typedef struct tagMatrixInfo
{
int i32nLine;
int i32nCol;
tagMatrixInfo()
{
i32nLine = i32nCol = 0;
}
}S_MatrixInfo;
S_MatrixInfo GetMax2X2Matrix(int **ppMatrix, int nLine, int nCol)
{
assert(ppMatrix);
assert(nLine >= 2);
assert(nCol >= 2);
S_MatrixInfo sMaxMatrixInfo;
int nMaxValue = 0, nTempValue = 0;
for (int i32I = 0; i32I < nLine - 1; i32I++)
{
for (int i32J = 0; i32J < nCol - 1; i32J++)
{
nTempValue += (ppMatrix[i32I][i32J] + ppMatrix[i32I][i32J+1]);
nTempValue += (ppMatrix[i32I+1][i32J] + ppMatrix[i32I+1][i32J+1]);
if (nTempValue > nMaxValue)
{
nMaxValue = nTempValue;
sMaxMatrixInfo.i32nLine = i32I;
sMaxMatrixInfo.i32nCol = i32J;
}
nTempValue = 0;
}
}
return sMaxMatrixInfo;
}
int _tmain(int argc, _TCHAR* argv[])
{
int i32I = 0, i32J = 0;
int i32nLine = 0, i32nCol = 0;
cin >> i32nLine >> i32nCol;
int **ppMatrix = new int *[i32nLine];
assert(ppMatrix);
for (i32I = 0; i32I < i32nLine; i32I++)
{
ppMatrix[i32I] = new int[i32nCol];
assert(ppMatrix[i32I]);
for (i32J = 0; i32J < i32nCol; i32J++)
{
cin >> ppMatrix[i32I][i32J];
}
}
S_MatrixInfo sMaxMatrixInfo = GetMax2X2Matrix(ppMatrix, i32nLine, i32nCol);
cout << endl << "最大的二維矩陣爲:" << endl;
for (i32I = sMaxMatrixInfo.i32nLine; i32I < sMaxMatrixInfo.i32nLine + 2; i32I++)
{
for (i32J = sMaxMatrixInfo.i32nCol; i32J < sMaxMatrixInfo.i32nCol + 2; i32J++)
{
cout << ppMatrix[i32I][i32J] << " ";
}
cout << endl;
}
return 0;
}
擴展:
如果題目是要求求最大的子矩陣呢,那麼我們就可以把矩陣每一豎直方向的排列,看做一個元素。
所以,矩陣就轉化成了我們熟悉的一維數組。
即以上矩陣,相當於:
a[1->n][1] a[1->n][2] ... a[1->n][i] .. a[1->n][j] .. a[1->n][n]
1->n 表示豎直方向,其中a[1->n][1]表示第一列中的所有元素相加後的值。
那麼,假定是5X5矩陣,那解法是:
第一行:a[1-5][1] a[1-5][2] a[1-5][3] a[1-5][4] a[1-5][5] 形成一個一維數組,該數組的最大和值爲Sum1.
第二行:a[2-5][1] a[2-5][2] a[2-5][3] a[2-5][4] a[2-5][5] 形成一個一維數組,該數組的最大和值爲Sum2.
第三行:a[3-5][1] a[3-5][2] a[3-5][3] a[3-5][4] a[3-5][5] 形成一個一維數組,該數組的最大和值爲Sum3.
第四行:a[4-5][1] a[4-5][2] a[4-5][3] a[4-5][4] a[4-5][5] 形成一個一維數組,該數組的最大和值爲Sum4.
第五行:a[5][1] a[5][2] a[5][3] a[5][4] a[5][5] 形成一個一維數組,該數組的最大和值爲Sum5.
然後比較Sum1到Sum5找出最大值就爲該矩陣的最大子矩陣所對應的和值.