1. 程式人生 > 其它 >【力扣-困難】85. 最大矩形

【力扣-困難】85. 最大矩形

技術標籤:leecode演算法leetcode

給定一個僅包含01、大小為rows x cols的二維二進位制矩陣,找出只包含1的最大矩形,並返回其面積。

示例 1:


輸入:matrix = [["1","0","1","0","0"],["1","0","1","1","1"],["1","1","1","1","1"],["1","0","0","1","0"]]

輸出:6
解釋:最大矩形如上圖所示。
示例 2:

輸入:matrix = []
輸出:0
示例 3:

輸入:matrix = [["0"]]
輸出:0
示例 4:

輸入:matrix = [["1"]]
輸出:1
示例 5:

輸入:matrix = [["0","0"]]
輸出:0

提示:

rows == matrix.length
cols == matrix[0].length
0 <= row, cols <= 200
matrix[i][j] 為 '0' 或 '1'

來源:力扣(LeetCode)
連結:https://leetcode-cn.com/problems/maximal-rectangle

【解答】

rowWidth[i][j]為矩陣第i行第j列元素的左邊連續1的數量;
遍歷矩陣,從當前行向上列舉以該點為右下角的全1矩形,記錄最大值:

int maximalRectangle(vector<vector<char>>& matrix) {
        int row = matrix.size();
        if (row == 0) return 0;
        int col = matrix[0].size();
        vector<vector<int>> rowWidth(row, vector<int>(col, 0));
        for(int i = 0;  i < row; i++){
            for(int j = 0; j < col; j++){
                if (matrix[i][j] == '1')
                    rowWidth[i][j] = (j == 0 ? 0 : rowWidth[i][j-1]) + 1;
            }
        }
        int ans = 0;
        for(int i = 0;  i < row; i++){
            for(int j = 0; j < col; j++){
                if (matrix[i][j] == '0') continue;
                int minWidth = rowWidth[i][j], area = minWidth;
                for(int k = i - 1; k >= 0; k--){
                    minWidth = min(minWidth, rowWidth[k][j]);
                    area = max(area, (i - k + 1) * minWidth);
                }
                ans = max(ans, area);
            }
        }
        return ans;
    }

【單調棧】

套用柱狀圖求最大矩形面積的方法,https://blog.csdn.net/qq_39380838/article/details/111746766

int maximalRectangle(vector<vector<char>>& matrix) {
        int row = matrix.size();
        if (row == 0) return 0;
        int col = matrix[0].size();
        vector<vector<int>> rowWidth(row, vector<int>(col, 0));
        for(int i = 0;  i < row; i++){
            for(int j = 0; j < col; j++){
                if (matrix[i][j] == '1')
                    rowWidth[i][j] = (j == 0 ? 0 : rowWidth[i][j-1]) + 1;
            }
        }
        int ans = 0;
        for(int j = 0; j < col; j++){
            stack<int> monoStack;
            vector<int> up(row), down(row, row);
            for(int i = 0;  i < row; i++){
                while (!monoStack.empty() && rowWidth[monoStack.top()][j] >= rowWidth[i][j]){
                    down[monoStack.top()] = i;
                    monoStack.pop();
                }
                up[i] = monoStack.empty() ? -1 : monoStack.top();
                monoStack.push(i);
            }
            for(int i = 0; i < row; i++){
                ans = max(ans, rowWidth[i][j] * (down[i] - up[i] - 1));
            }
        }
        return ans;
    }