public static int largestRectangleArea(int[] height ){ int maxArea = 0; Stack<Integer> s = new Stack<>(); int i = 0; while (i <= height.length){ int h = (i == height.length ? 0 : height[i]); if(s.isEmpty() || h >= height[s.peek()]){ s.push(i); i++; }else { int t = s.pop(); maxArea = Math.max(maxArea, height[t] * (s.isEmpty() ? i : i - s.peek() - 1)); } } return maxArea; }
Maximal Rectangle此题是之前那道的 Largest Rectangle in Histogram直方图中最大的矩形 的扩展,这道题的二维矩阵每一层向上都可以看做一个直方图,输入矩阵有多少行,就可以形成多少个直方图,对每个直方图都调用 Largest Rectangle in Histogram 直方图中最大的矩形 中的方法,就可以得到最大的矩形面积。那么这道题唯一要做的就是将每一层构成直方图,由于题目限定了输入矩阵的字符只有 ‘0’ 和 ‘1’ 两种,所以处理起来也相对简单。方法是,对于每一个点,如果是‘0’,则赋0,如果是 ‘1’,就赋之前的height值加上1。具体参见代码如下:
public static int maximalRectangle(char[][] matrix) { if(matrix == null || matrix.length == 0 || matrix[0].length == 0) return 0;
int[] height = new int[matrix[0].length]; for(int i = 0; i < matrix[0].length; i ++){ if(matrix[0][i] == '1') height[i] = 1; } int result = largestRectangleArea(height); for(int i = 1; i < matrix.length; i ++){ resetHeight(matrix, height, i); result = Math.max(result, largestRectangleArea(height)); } return result; }
private static void resetHeight(char[][] matrix, int[] height, int idx){ for(int i = 0; i < matrix[0].length; i ++){ if(matrix[idx][i] == '1') height[i] += 1; else height[i] = 0; } }
public static int largestRectangleArea(int[] height ){ int maxArea = 0; Stack<Integer> s = new Stack<>(); int i = 0; while (i <= height.length){ int h = (i == height.length ? 0 : height[i]); if(s.isEmpty() || h >= height[s.peek()]){ s.push(i); i++; }else { int t = s.pop(); maxArea = Math.max(maxArea, height[t] * (s.isEmpty() ? i : i - s.peek() - 1)); } } return maxArea; }