java最大子方阵_最大子方阵

这篇博客探讨了如何使用Java实现寻找给定矩阵中最大子方阵的算法,包括动态规划和暴力搜索两种方法。作者展示了不同的实现思路,如通过检查每个点的上、下、左、右连续相同元素的数量来确定最大子方阵,以及利用二维数组记录相邻元素的连续相同长度等。博客中包含了多个示例代码,用于解释和验证算法的有效性。
摘要由CSDN通过智能技术生成

5

class SubMatrix {

private:

bool checkRec(vector>& mat, int x, int y, int len)

{

int digit = mat[x][y];

for (int i = 0; i < len; ++i) if (mat[x + i][y] != digit || mat[x + i][y + len - 1] != digit) return false;

for (int j = 0; j < len; ++j) if (mat[x][y + j] != digit || mat[x + len - 1][y + j] != digit) return false;

return true;

}

public:

int maxSubMatrix(vector> mat, int n)

{

int maxLen = 1;

for (int i = 0; i < n - maxLen; ++i)

{

for (int j = 0; j < n - maxLen; ++j)

{

for (int k = maxLen + 1; max(i, j) + k - 1 < n; ++k)

{

if (checkRec(mat, i, j, k)) maxLen = max(maxLen, k);

}

}

}

return maxLen;

}

};

发表于 2017-07-02 18:47:41

回复(3)

9

import java.util.*;

public class SubMatrix {

/**

* 使用动态规划

* left[i][j]: 坐标[i,j]的左边有连续相同的数个数,包含自己

* above[i][j]: 坐标[i,j]的上边有连续相同的数个数,包含自己

* 初始值:left[i][j]=1; above[i][j]=1

* 递推式:

* left[i][j]=left[i][j-1]+1, mat[i][j]==mat[i][j-1];

* left[i][j]=1, mat[i][j]!=mat[i][j-1];

* above[i][j]=above[i-1][j]+1, mat[i][j]==mat[i-1][j];

* above[i][j]=1, mat[i][j]!=mat[i-1][j];

* 在递推的过程中求解: mat[i][j]==mat[i][j-1]&&mat[i][j]==mat[i-1][j]

* @param mat

* @param n

* @return

*/

public int maxSubMatrix(int[][] mat, int n) {

int max = 1;

int[][] left = new int[n][n];

int[][] above = new int[n][n];

initial(mat, n, left, above);

for (int i = 1; i < n; i++) {

for (int j = 1; j < n; j++) {

if (mat[i - 1][j] != mat[i][j] || mat[i][j - 1] != mat[i][j]) {

if (mat[i - 1][j] != mat[i][j]

&& mat[i][j - 1] != mat[i][j]) {

left[i][j] = 1;

above[i][j] = 1;

} else if (mat[i][j - 1] != mat[i][j]) {

left[i][j] = 1;

above[i][j] = above[i-1][j] + 1;

} else {

above[i][j] = 1;

left[i][j] = left[i][j-1] + 1;

}

} else {

left[i][j] = left[i][j - 1] + 1;

above[i][j] = above[i - 1][j] + 1;

int min = Math.min(left[i][j - 1], above[i - 1][j]);

for (int k = min; k > 0 && min>=max; k--) {//此处求解结果

if (above[i][j - min] >= (min + 1)

&& left[i - min][j] >= (min + 1)) {

max = Math.max(max, min + 1);

break;

}

}

}

}

}

return max;

}

public void initial(int[][] mat, int n, int[][] left, int[][] above) {

left[0][0] = 1;

Arrays.fill(above[0], 1);

for (int i = 1; i < n; i++) {

left[i][0] = 1;

if (mat[0][i] != mat[0][i - 1]) {

left[0][i] = 1;

} else {

left[0][i] = left[0][i - 1] + 1;

}

}

for (int i = 1; i < n; i++) {

if (mat[i][0] != mat[i - 1][0]) {

above[i][0] = 1;

} else {

above[i][0] = above[i - 1][0] + 1;

}

}

}

}

发表于 2016-08-05 23:02:46

回复(6)

5

class SubMatrix {

public:

int maxSubMatrix(vector > mat, int n) {

//选定最大子方阵的边长,选择顶点,判断是合法

int maxLength = n;

while(maxLength){

for(int i = 0; i <= n - maxLength; ++i){

for(int j = 0; j <= n - maxLength; ++j){

int pixel = mat[i][j];

bool flag = true;

for(int k = 0; k < maxLength; ++k){

int top = mat[i][j + k]; // 上边的线

int bottom = mat[i + maxLength - 1][j + k]; // 下边的线

int left = mat[i + k][j]; // 左边的线

int right = mat[i + k][j + maxLength -1]; // 右边的线

if(top != pixel || bottom != pixel || left != pixel || right != pixel){

flag = false;

break;

}

}

if(flag)

return maxLength;

}

}

maxLength--;

}

return 0;

}

};

发表于 2017-05-05 21:44:55

回复(3)

2

import java.util.*;

public class SubMatrix {

public int maxSubMatrix(int[][] mat, int n) {

int max = 1;

int[][] left = new int[n][n];

int[][] above = new int[n][n];

initial(mat, n, left, above);

for (int i = 1; i 

for (int j = 1; j 

if (mat[i][j]==mat[i-1][j] && mat[i][j]==mat[i][j-1]) {

left[i][j] = left[i][j-1]+1;

above[i][j] = above[i-1][j]+1;

int len = Math.min(left[i][j],above[i][j]);

for(int k=len-1;k>0&&k+1>max;k--){

if(above[i][j-k]>k && left[i-k][j]>k){

max = k+1;

break;

}

}

} else if(mat[i][j]!=mat[i-1][j] && mat[i][j]!=mat[i][j-1]){

left[i][j] = 1;

above[i][j] = 1;

} else if(mat[i][j]==mat[i][j-1]){

left[i][j] = left[i][j-1]+1;

above[i][j] = 1;

} else if(mat[i][j]==mat[i-1][j]){

left[i][j] = 1;

above[i][j] = above[i-1][j]+1;

}

}

}

return max;

}

public void initial(int[][] mat, int n, int[][] left, int[][] above) {

for(int i=0;i

left[i][0] = 1;

above[0][i] = 1;

}

for(int j=1;j

if(mat[0][j]==mat[0][j-1])

left[0][j] = left[0][j-1]+1;

else

left[0][j] = 1;

}

for(int i=1;i

if(mat[i][0]==mat[i-1][0])

above[i][0] = above[i-1][0]+1;

else

above[i][0] = 1;

}

}

}

发表于 2020-03-05 20:02:57

回复(0)

2

import java.util.*;

public class SubMatrix {

public int maxSubMatrix(int[][] mat, int n) {

// write code here

for(int size = n ; size>=1;size--)

for(int row = 0;row< n ;row++){

for(int col =0;col< n ;col++){

if(isSquare0(mat,row,col,size) || isSquare1(mat,row,col,size)){

return size;

}

}

}

return -1;

}

// 第row 行 col列 (0开始) 开始的矩阵,矩阵大小是 size

public boolean isSquare0(int[][] mat, int row, int col,int size){

// 检查 上 下 边界

for(int j = 0; j < size; j++){

if(col+j>=mat.length || row+size-1>=mat.length)

return false;

if(mat[row][col+j] == 1)

return false;

if(mat[row+size-1][col+j] ==1)

return false;

}

// 检测 左 右 边界

for(int i = 0;i< size - 1;i++){

if(row+i>=mat.length || col+size-1>=mat.length)

return false;

if( mat[row+i][col] == 1)

return false;

if(mat[row+i][col+size-1]==1)

return false;

}

return true;

}

public boolean isSquare1(int[][] mat, int row, int col,int size){

// 检查 上 下 边界

for(int j = 0; j < size; j++){

if(col+j>=mat.length || row+size-1>=mat.length)

return false;

if(mat[row][col+j] == 0)

return false;

if(mat[row+size-1][col+j] ==0)

return false;

}

// 检测 左 右 边界

for(int i = 0;i< size - 1;i++){

if(row+i>=mat.length || col+size-1>=mat.length)

return false;

if( mat[row+i][col] == 0)

return false;

if(mat[row+i][col+size-1]==0)

return false;

}

return true;

}

}

发表于 2016-02-26 22:09:45

回复(0)

2

/*

根据20150909期左老师的视频将的方法做的,这里有一点不同都为0组成的方形也要与最大边长比较。

这里主要的问题是验证过程,需要遍历wide到1。

*/

class SubMatrix {

public:

int maxSubMatrix(vector > mat, int n) {

// write code here

if(n == 0) return 0;

vector > matA = mat;//坐标点下方连续1的个数

vector > matB = mat;//坐标点右方连续1的个数

vector > matAA = mat;//坐标点下方连续0的个数

vector > matBB = mat;//坐标点右方连续0的个数

int i,j;

int len = 0;

int wide;

for(i=n-1;i>=0;--i){

for(j=n-1;j>=0;--j){

if(mat[i][j] == 0){

matA[i][j] = 0;

matB[i][j] = 0;

if(i == n-1){

matAA[i][j] = 1;

}else{

matAA[i][j] = matAA[i+1][j]+1;

}

if(j == n-1){

matBB[i][j] = 1;

}else{

matBB[i][j] = matBB[i][j+1]+1;

}

}else {

if(i == n-1){

matA[i][j] = 1;

}else{

matA[i][j] = matA[i+1][j]+1;

}

if(j == n-1){

matB[i][j] = 1;

}else{

matB[i][j] = matB[i][j+1]+1;

}

matAA[i][j] = 0;

matBB[i][j] = 0;

}

}

}

for(i=0;i

for(j=0;j

if(mat[i][j] == 0){

wide = min(matAA[i][j],matBB[i][j]);

while(wide>0){

if(matAA[i][j+wide-1] >= wide && matBB[i+wide-1][j] >= wide){

len = len

}

wide--;

}

}else{

wide = min(matA[i][j],matB[i][j]);

while(wide>0){

if(matA[i][j+wide-1] >= wide && matB[i+wide-1][j] >= wide){

len = len

}

wide--;

}

}

}

}

return len;

}

};

发表于 2015-09-10 15:23:11

回复(0)

1

//参考票数最多的答案,对计算过程做了优化,同样是使用两个数组的动态规划思路

//1、对矩阵中的每个点设置一个竖方向与其连续相同像素的点数目,一个水平方向与其连续相同像素点数目

//2、最大子方阵即为当该点左侧和上侧的像素都与其相同,此时相当于知道了矩阵的下边和右边长度

//往上遍历点若其左侧连续点数目不低于短边(因为是方阵所以只能选最短边),同理,向左遍历点,

//若其上侧连续点数目不低于短边,则此时已经找到一个满足题目要求的子方阵。

class SubMatrix {

public:

int maxSubMatrix(vector > mat, int n) {

// write code here

if(n < 1)

return 0;

vector> left(n,vector(n,1));

vector> above(n,vector(n,1));

for(int i=1;i

{

if(mat[0][i] == mat[0][i-1])

{

left[0][i] = left[0][i-1] + 1;

}

if(mat[i][0] == mat[i-1][0])

{

above[i][0] = above[i-1][0] + 1;

}

}

int min_n = 0;

int max_n = 1;

for(int i=1;i

{

for(int j=1;j

{

if(mat[i][j]==mat[i-1][j] && mat[i][j]==mat[i][j-1])

{

left[i][j] = left[i][j-1]+1;

above[i][j] = above[i-1][j]+1;

min_n = min(left[i][j],above[i][j]);

if(min_n <= max_n)

continue;

for(int k=0;k

{

if(above[i][j-k]>=min_n && left[i-k][j]>=min_n)

{

if(k+1 > max_n)

{

max_n = k+1;

}

}

}

}else

{

if(mat[i][j]==mat[i-1][j])

above[i][j] = above[i-1][j]+1;

else if(mat[i][j]==mat[i][j-1])

left[i][j] = left[i][j-1]+1;

}

}

}

return max_n;

}

};

发表于 2020-07-09 00:20:18

回复(0)

1

为每个点赋予四个带有上、下、左、右四个向量,向量长度等于该点颜色向该反向最多延伸的距离,当且仅当子方阵左上角的点的右、下向量长度大于等于子方阵边长,右下角的点的左、上向量长度大于等于子方阵边长时满足要求。

这个算法的第一个关键所在是如何计算向量长度,我的算法只写到了纯暴力计算的长度,优化的思路:

例如

1.如果一个点的right向量长度是3,那么它右边2个点的right向量长度依次为:2、1

2.如果一个点的left向量长度为3,right向量长度为3,那么他右面的2个点的left向量长度依次为:4、5

等等

程序有两个要注意的点:二维vector的初始化,边缘点向量长度的计算。 vector > up(n);

vector > down(n);

vector > left(n);

vector > right(n);

for (int i = 0; i < n; i++)

{

up[i].resize(n);

down[i].resize(n);

left[i].resize(n);

right[i].resize(n);

}

int max = 1;

for (int i = 0; i < n; i++)

{

for (int j = 0; j < n; j++)

{

for (int k = j; k < n; k++)

{

if (k == n - 1)

{

right[i][j] = k - j + 1;

break;

}

if (mat[i][k + 1] != mat[i][j])

{

right[i][j] = k - j + 1;

break;

}

}

for (int k = j; k >= 0; k--)

{

if (k == 0)

{

left[i][j] = j - k + 1;

break;

}

if (mat[i][k - 1] != mat[i][j])

{

left[i][j] = j - k + 1;

break;

}

}

for (int k = i; k < n; k++)

{

if (k == n - 1)

{

down[i][j] = k - i + 1;

break;

}

if (mat[k + 1][j] != mat[i][j])

{

down[i][j] = k - i + 1;

break;

}

}

for (int k = i; k >= 0; k--)

{

if (k == 0)

{

up[i][j] = i - k + 1;

break;

}

if (mat[k - 1][j] != mat[i][j])

{

up[i][j] = i - k + 1;

break;

}

}

}

}

/*向量长度矩阵测试

cout << "r" << endl;

for (int i = 0; i < n; i++)

{

for (int j = 0; j < n; j++)

{

cout << right[i][j];

}

cout << endl;

}

cout << "d" << endl;

for (int i = 0; i < n; i++)

{

for (int j = 0; j < n; j++)

{

cout << down[i][j];

}

cout << endl;

}

cout << "l" << endl;

for (int i = 0; i < n; i++)

{

for (int j = 0; j < n; j++)

{

cout << left[i][j];

}

cout << endl;

}

cout << "u" << endl;

for (int i = 0; i < n; i++)

{

for (int j = 0; j < n; j++)

{

cout << up[i][j];

}

cout << endl;

}*/

for (int i = 0; i < n; i++)

{

for (int j = 0; j < n; j++)

{

for (int a = i + 1, b = j + 1; b < n&&a < n; a++, b++)

{

if (right[i][j] >= b - j + 1 && down[i][j] >= a - i + 1 && left[a][b] >= b - j + 1 && up[a][b] >= a - i + 1)

{

if (max < b - j + 1)

{

max = b - j + 1;

}

}

}

}

}

return max;

}

};

编辑于 2019-03-30 18:23:36

回复(0)

1

//想半天别的不如此土法

class SubMatrix {

public:

int maxSubMatrix(vector > mat, int n) {

// write code here

int l=n;

int left,right,down,up;

while(l)

{

for(int i=0;i<=n-l;i++)

{

for(int j=0;j<=n-l;j++)

{

int val=mat[i][j];

int p=0;

for(;p

{

left=mat[i+p][j];

right=mat[i+p][j+l-1];

up=mat[i][j+p];

down=mat[i+l-1][j+p];

if(left!=val||up!=val||down!=val||right!=val)

break;

}

if(p==l)

return l;

}

}

l--;

}

return 1;

}

};

发表于 2018-07-05 10:24:05

回复(0)

1

/*暴力法,用例复杂度不高,侥幸通过*/

import java.util.*;

public class SubMatrix {

public int maxSubMatrix(int[][] mat, int n) {

// write code here

int max=0;

for (int i=0; i

for (int j=0; j

int maxlen = LentoEdge(n,i,j);

for (int k=0; k<=maxlen; k++){

if (fun(mat,k,i,j) && k>max){

max = k;

}

}//for

}//for

}//for

return max;

}

public boolean fun (int[][] mat, int n, int x, int y){//以(x,y)为左上角点,边长为n是否满足边框颜色一致

int temp = mat[x][y];

for (int i=0; i

if(mat[x+i][y] != temp)

return false;

}

for (int i=0; i

if(mat[x][y+i] != temp)

return false;

}

for (int i=0; i

if(mat[x+n-1][y+i] != temp)

return false;

}

for (int i=0; i

if(mat[x+i][y+n-1] != temp)

return false;

}

return true;

}

public int LentoEdge(int n, int x, int y){

return Math.min(n-x, n-y);

}

}

发表于 2017-11-01 09:27:16

回复(0)

1

class SubMatrix {

public:

int maxSubMatrix(vector > mat, int n) {

// int x = 0;//测试长度为x大小的方阵

int max=1;

int m=0;

for(int i=0;i

for(int j=0;j

{

int k;

k = mat[i][j];

int y;//行列余量判断,即测试方阵x所能达到的最大维数

if(i

y = n-j;

else y = n-i;

for(int x=1;x<=y;x++)

{

for(int l=0;l

{

if((mat[i][j+l]!=k)||(mat[i+l][j]!=k)||(mat[i+l][j+x-1]!=k)||(mat[i+x-1][j+l]!=k))

break;

else m=l+1;//误点:开始总是吧x的值赋给m,其实子方阵是否有效取决于l,因为x可能取的大于 }

if(max < m)

max = m;

}

}

return max;

}

};

编辑于 2017-07-31 21:15:50

回复(2)

1

int maxSubMatrix(vector > mat, int n) {

vector ones(n, 1);

vector> left(n, ones);//当前点左边连续相同的点个数(算自己)

vector> above(n, ones);//当前点上边连续相同的点个数(算自己)

initail(mat, n, left, above);

int maxLength = 1;

for (int i = 1; i < n; i++) {

for (int j = 1; j < n; j++) {

if (mat[i][j] != mat[i][j - 1] || mat[i][j] != mat[i - 1][j]) {

if (mat[i][j] != mat[i][j - 1] && mat[i][j] != mat[i - 1][j]) {

left[i][j] = above[i][j] = 1;

}

else if (mat[i][j] != mat[i][j - 1]) {

left[i][j] = 1;

above[i][j] = above[i - 1][j] + 1;

}

else if (mat[i][j] != mat[i - 1][j]) {

above[i][j] = 1;

left[i][j] = left[i][j - 1] + 1;

}

}

else {

left[i][j] = left[i][j - 1] + 1;

above[i][j] = above[i - 1][j] + 1;

int minLength = min(left[i][j - 1], above[i - 1][j]);//由于是方阵,长宽要一致,因此取二者最小的那个

for (int length = minLength; length > 0 && length >= maxLength; length--) {//在最小中找最大

if (left[i - length][j] >= minLength + 1 && above[i][j - length] >= minLength + 1) {//考察对边的长度

maxLength = max(maxLength, length + 1);

}

}

}

}

}

return maxLength;

}

void initail(vector> mat, int n, vector> &left, vector> &above) {

for (int i = 1; i < n; i++) {

if (mat[0][i] == mat[0][i - 1]) {

left[0][i] = left[0][i - 1] + 1;

}

if (mat[i][0] == mat[i - 1][0]) {

above[i][0] = above[i - 1][0] + 1;

}

}

}

编辑于 2017-07-14 11:11:10

回复(0)

1

都是暴力的,能不能有技巧?

发表于 2017-07-13 19:04:12

回复(0)

1

class SubMatrix:

def maxSubMatrix(self, mat, n):

B = [[[0, 0] for i in range(n + 1)] for i in range(n + 1)] #预处理,构建黑白最长边,降为O(N^3)

H = [[[0, 0] for i in range(n + 1)] for i in range(n + 1)]

for i in xrange(n - 1, -1, -1):

for j in xrange(n - 1, -1, -1):

if mat[i][j] == 1:

fill(B, i, j)

else:

fill(H, i, j)

for t in xrange(n, 0, -1):

for i in xrange(n - t + 1):

for j in xrange(n - t + 1):

if isSqure(B, i, j, t) or isSqure(H, i, j, t): #判断黑边和白边是否在范围内

return t

def fill(A, i, j):

A[i][j][0] = A[i + 1][j][0] + 1

A[i][j][1] = A[i][j + 1][1] + 1

def isSqure(A, i, j, t):

return A[i][j][0] >= t and A[i][j][1] >= t and A[i + t - 1][j][1] >= t and A[i][j + t - 1][0] >= t

发表于 2017-03-22 18:20:00

回复(0)

1

struct NODE

{

int left;

int right;

int up;

int bottom;

NODE():left(1),right(1),up(1),bottom(1){}

};

class SubMatrix {

public:

void count(vector> &num,vector>& mat,int n)

{

for(int i=1;i

{

if(mat[0][i] == mat[0][i-1])

num[0][i].left = num[0][i-1].left + 1;

if(mat[i][0] == mat[i-1][0])

num[i][0].up = num[i-1][0].up + 1;

}

for(int i=n-2;i>=0;i--)

{

if(mat[n-1][i] == mat[n-1][i+1])

num[n-1][i].right = num[n-1][i+1].right + 1;

if(mat[i][n-1] == mat[i+1][n-1])

num[i][n-1].bottom = num[i+1][n-1].bottom + 1;

}

for(int i=1;i

{

for(int j=1;j

{

if(mat[i][j] == mat[i-1][j])

num[i][j].up = num[i-1][j].up + 1;

if(mat[i][j] == mat[i][j-1])

num[i][j].left = num[i][j-1].left + 1;

}

}

for(int i=n-2;i>=0;i--)

{

for(int j=n-2;j>=0;j--)

{

if(mat[i][j] == mat[i+1][j])

num[i][j].bottom = num[i+1][j].bottom + 1;

if(mat[i][j] == mat[i][j+1])

num[i][j].right = num[i][j+1].right + 1;

}

}

}

int getmax(vector> &num,vector> &mat,int n)

{

int res = 1;

for(int i=1;i

{

for(int j=1;j

{

int cur_min = min(num[i][j].up,num[i][j].left);

if(cur_min <= res)

continue;

int fence = cur_min;

int nr,nc;

while(--fence)

{

nr = i-fence;

nc = j-fence;

if(mat[nr][nc] != mat[i][j])

continue;

int cur_min2 = min(num[nr][nc].right,num[nr][nc].bottom);

if(cur_min2 >= fence+1)

{

res = max(res,fence+1);

break;

}

}

}

}

return res;

}

int maxSubMatrix(vector > mat, int n) {

if(n < 2)

return 1;

vector> node(n,vector(n));

count(node,mat,n);

return getmax(node,mat,n);

}

};

n三方的算法,再剪枝,主要思想就是维护每个点的上下左右连续的0或1的个数。然后遍历每个点求解。

编辑于 2015-07-30 12:55:20

回复(0)

0

def maxSubMatrix(self, mat, n):

for j in range(n,1,-1):

for x in range(n-j+1):

for y in range(n-j+1):

for k in range(j):

t = 0

m0 = mat[x][y]

m1 = mat[x][y+k]

m2 = mat[x+k][y]

m3 = mat[x+k][y+j-1]

m4 = mat[x+j-1][y+k]

if m1 != m0&nbs***bsp;m2 != m0&nbs***bsp;m3 != m0&nbs***bsp;m4 != m0:

break

else:

k += 1

if k == j:

return j

return 1

发表于 2020-08-21 17:33:02

回复(0)

0

struct Count{

int n_right;//右边颜色相同连续子段长度

int n_down;

Count(){

n_right = 1;

n_down = 1;

}

friend ostream& operator<

o<

return o;

}

};

class SubMatrix {

public:

int maxSubMatrix(vector > mat, int n) {

// write code here

if(n==0) return 0;

//1.暴力解法

//2.事先统计每个位置上右边、下边连续段长度O(n^3)

vector > counts(n,vector());//统计所有坐标位置上的右边、下边连续数字数目

for(auto i=0;i

for(auto j=0;j

counts[i].push_back(Count());

}

}

//O(n^2)

//预先计算每个位置右边、下边的连续长度

for(auto i=n-1;i>=0;i--){

for(auto j=n-1;j>=0;j--){

if(i!=n-1){

if(mat[i][j]==mat[i+1][j]){

counts[i][j].n_down = counts[i+1][j].n_down+1;

}

}

if(j!=n-1){

if(mat[i][j]==mat[i][j+1]){

counts[i][j].n_right = counts[i][j+1].n_right+1;

}

}

}

}

//PR(counts);

int ans = 0;

//计算i,j位置开始的最大方块(长度从右、下两边中最小连续段长度开始)

for(auto i=0;i

for(auto j=0;j

for(auto len=min(counts[i][j].n_right,counts[i][j].n_down);len>0;len--){

if(counts[i+len-1][j].n_right>=len and counts[i][j+len-1].n_down>=len){

ans = max(ans,len);

break;

}

}

}

}

return ans;

}

};

发表于 2020-02-09 09:17:34

回复(0)

0

public static int maxSubMatrix(int[][] mat, int n) {

// write code here

int max = n;//设定最大子方阵边长max为n

while(max > 1) {//当最大子方阵边长为1时退出死循环

//变量startY,startX代表方阵的左上角定点,确定测试方阵

for(int startY = 0; startY <= n-max; startY++) {

//n为总方阵的边长,max为测试方阵的边长

for(int startX = 0; startX <= n-max; startX++) {

//n - max + 1为测试方阵的个数

boolean flag = true;//true代表测试结果成立

int k = mat[startY][startX];//k为方阵左上角数据

int moveX = startX;

int moveY = startY; //moveX,moveY抽象移动光标测试

int endX = max + startX - 1;

int endY = max + startY - 1;//endX,endY为测试矩阵终点

//测试子矩阵除右上角的最上边

while(flag == true && moveX 

if(mat[moveY][moveX] != k) {

flag = false;//若存在一数据不相同,变为false

break;//跳出循环

}

moveX++;//横坐标累加

}//以下循环同理

//测试子矩阵除右下角的最右边

while(flag == true && moveY 

if(mat[moveY][moveX] != k) {

flag = false;

break;

}

moveY++;

}

//测试子矩阵除左下角的最下边

while(flag == true && moveX > startX) {

if(mat[moveY][moveX] != k) {

flag =false;

break;

}

moveX--;

}

//测试子矩阵除左上角的最左边

while(flag == true && moveY > startY) {

if(mat[moveY][moveX] != k) {

flag = false;

break;

}

moveY--;

}

//若仍为true,说明测试结果成立,返回子阵的最大边长

if(flag == true)  return max;

}

}

//若测试的所有定点均不满足最大边长条件,最大边长递减依次测试

max--;

}

return max;

}

发表于 2019-09-22 13:47:14

回复(0)

0

class SubMatrix {

public:

int maxSubMatrix(vector > mat, int n) {

// write code here

int maxLen=n,up,down,left,right;

while(maxLen){

for(int i=0;i+maxLen<=n;i++){

for(int j=0;j+maxLen<=n;j++){

up=left=1;

down=right=0;

for(int m=1;m

if(mat[i][j+m]==mat[i][j])up++;

else break;

}

for(int m=1;m

if(mat[i+m][j]==mat[i][j])left++;

else break;

}

for(int m=0;m

if(mat[i+maxLen-1][j+m]==mat[i][j])down++;

else break;

}

for(int m=0;m

if(mat[i+m][j+maxLen-1]==mat[i][j])right++;

else break;

}

if(up==maxLen && down==maxLen && left==maxLen && right==maxLen)return maxLen;

}

}

maxLen--;

}

return 1;

}

};

发表于 2019-06-19 22:51:31

回复(0)

0

public class SubMatrix {

public int maxSubMatrix(int[][] mat, int n) {

// write code here

for (int i = n; i >= 1; i--) {

if (findSquareWithSize(mat, i)) {

return i;

}

}

return -1;

}

public boolean findSquareWithSize(int[][] mat, int squareSize) {

int cnt = mat.length - squareSize + 1;

for (int row = 0; row < cnt; row++) {

for (int col = 0; col < cnt; col++) {

if (isSquare(mat, row, col, squareSize, 1) || isSquare(mat, row, col, squareSize, 0)) {

return true;

}

}

}

return false;

}

public boolean isSquare(int[][] mat, int row, int col, int size, int flag) {

//检查上边界和下边界

for (int i = 0; i < size; i++) {

if (mat[row][col + i] == flag) {

return false;

}

if (mat[row + size - 1][col + i] == flag) {

return false;

}

}

//检查左边界和右边界

for (int i = 1; i < size - 1; i++) {

if (mat[row + i][col] == flag) {

return false;

}

if (mat[row + i][col + size - 1] == flag) {

return false;

}

}

return true;

}

}

发表于 2019-02-17 17:42:28

回复(0)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值