题目:
Given a 2D binary matrix filled with 0's and 1's, find the largest rectangle containing all ones and return its area.
题意:
给定一个包含0和1的二维二进制矩阵,找出包含所有1的最大矩形并返回其面积。
解题思路:
当时我是这么想的直接双重循环,找到等于1的数字,然后sum++。然后看了下别人的解析,再看自己的代码简直是too youth too simple,哈哈
看了下别人的代码,发现什么都没看懂。为啥要把那一行看成一个直方图等,直接懵逼了。然后就跳过了
机缘巧合下写了这道题(虽然也是参考别人的(不要脸.jpg))直方图中最大的矩形,脑子突然灵光一现,发现这么和题有点相似
好了,思路如下:
把每一层向上可以看成一个直方图,有多少行就有多少个直方图,对每个直方图我们都可以调用直方图中最大的矩形这个函数,然后在每一行结束后不断求出最大面积即可
那么如何把每一层构造成一个直方图呢,通过判断当前值是否为‘0’,是的话就赋0,不是就在high[j]上加1。仔细看的话构造直方图的时候是不是有点动态规划的赶脚。
下面开始展示Java代码:
public static int maximalRectangle(char[][] matrix) {
if(matrix == null || matrix.length <= 0 || matrix[0].length <= 0) {
return 0;
}
int row = matrix.length;
int col = matrix[0].length;
int[] high = new int[col+1];
int maxArea = 0;
for(int i = 0 ; i < row ;i++) {
for(int j = 0 ; j < col ; j++) {
high[j] = matrix[i][j] == '0' ? 0:high[j]+1;
}
maxArea = Math.max(largestRectangleArea2(high), maxArea);
}
return maxArea;
}
public static int largestRectangleArea2(int[] height) {
if(height == null) {
return 0;
}
int res = 0;
Stack<Integer> stack = new Stack<Integer>();
for(int i = 0;i < height.length; i++) {
if(stack.isEmpty() || stack.peek() <= height[i]) {
stack.push(height[i]);
}
else {
int count = 0;
while(!stack.isEmpty() && stack.peek() > height[i]) {
count++;
res = Math.max(res, count*stack.peek());
stack.pop();
}
while(count-- > 0) {
stack.push(height[i]);
}
stack.push(height[i]);
}
}
int count = 1;
while(!stack.isEmpty()) {
res = Math.max(res, count*stack.peek());
stack.pop();
count++;
}
return res;
}