栈相关问题-使用单调栈解决最大矩形问题

120 阅读1分钟

解决最大矩形问题leetcode【85】

题目描述

给定一个仅包含 0 和 1 、大小为 rows x cols 的二维二进制矩阵,找出只包含 1 的最大矩形,并返回其面积。

单调栈解答

借助于就柱状图中最大矩形面积解答该问题;

  • 算出每一行的各个点的连续高度
    • 使用单调栈求出该行最大矩形面积
  • 根据每一行最大的面积求出最大面积

运行效率

_QD8E6(${6F0)Y5BUU(@11T.png

代码如下

function maximalRectangle(matrix: string[][]): number {
  if (!matrix.length) return 0;
  const dp: number[][] = [];
  let res = 0;

  initDp();
  matrix.forEach((item, index) => aesQueue(index));

  return res;

  function aesQueue(row: number) {
    let stack = [];
    stack.push(0);
    let ci = 1;
    while (ci < dp[row].length) {
      while (dp[row][ci] < dp[row][stack[stack.length - 1]]) {
        const height = dp[row][stack.pop()];
        const width = !stack.length ? ci : ci - stack[stack.length - 1] - 1;
        const area = width * height;
        res = res > area ? res : area;
      }
      stack.push(ci++);
    }
    ci = stack[stack.length - 1] + 1;
    while (stack.length > 1) {
      const height = dp[row][stack.pop()];
      const width = !stack.length ? ci : ci - stack[stack.length - 1] - 1;
      const area = width * height;
      res = res > area ? res : area;
    }

    if (stack.length === 1) {
      const area = dp[row].length * dp[row][stack.pop()];
      res = res > area ? res : area;
    }
  }

  function initDp() {
    if (matrix.length) {
      dp.push(matrix[0].map((item) => (item === "0" ? 0 : 1)));
    }
    for (let rowIndex = 1; rowIndex < matrix.length; rowIndex++) {
      dp[rowIndex] = [];
      matrix[rowIndex].forEach((col, colIndex) => {
        dp[rowIndex][colIndex] =
          parseInt(matrix[rowIndex][colIndex]) === 0
            ? 0
            : dp[rowIndex - 1][colIndex] + 1;
      });
    }
  }
}

const matrix = [
  ["1", "0", "1", "0", "0"],
  ["1", "0", "1", "1", "1"],
  ["1", "1", "1", "1", "1"],
  ["1", "0", "0", "1", "0"],
];

// const res = maximalRectangle(matrix);