zoukankan      html  css  js  c++  java
  • leetcode刷题笔记八十五题 最大矩形

    leetcode刷题笔记八十五题 最大矩形

    源地址:85. 最大矩形

    问题描述:

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

    示例:

    输入:
    [
    ["1","0","1","0","0"],
    ["1","0","1","1","1"],
    ["1","1","1","1","1"],
    ["1","0","0","1","0"]
    ]
    输出: 6

    /**
    本题主要讨论两种解法,第一种方法基于84题柱状图的单调栈解法结合动态规划
    将矩阵中的每一行作为一次x轴,对其中以该点能达到的最大高度视为柱状图高度处理即可
    时间复杂度:O(mn)
    空间复杂度:O(n)
    */
    import scala.collection.mutable
    object Solution {
        def maximalRectangle(matrix: Array[Array[Char]]): Int = {
            val rowLength = matrix.length
            if (rowLength == 0) return 0
            val colLength = matrix(0).length
            val dp = Array.fill(colLength)(0)
            var max = 0
    
            for(i <- 0 to rowLength-1){
                for(j <- 0 to colLength-1){
                    if(matrix(i)(j) == '1')   dp(j) += 1
                    else dp(j) = 0
                }
                //println(dp.mkString(" "))
                max = Math.max(max, largestRectangleArea(dp))
            }
            return max
        }
    
        def largestRectangleArea(heights: Array[Int]): Int = {
            val newHeights = Array(0).concat(heights).concat(Array(0))
            val length = newHeights.length
            val stack = new mutable.Stack[Int]()
            var area = 0
            stack.push(0)
    
            for(i <- 1 to length-1){
                while(newHeights(stack.top) > newHeights(i)){
                    val height = newHeights(stack.pop)
                    val width  = i - stack.top - 1
                    area = Math.max(area, height*width) 
                }
                stack.push(i)
            }
            return area
        }
    }
    
    /**
    法二是基于动态规划思想,使用heigth、left和right三个数组以行为单位计录该行中当前元素能够成矩阵的最大高度,最左侧及最右侧,用于计算矩阵面积。
    */
    import scala.collection.mutable
    object Solution {
        def maximalRectangle(matrix: Array[Array[Char]]): Int = {
            val rowLength = matrix.length
            if (rowLength == 0) return 0
            val colLength = matrix(0).length
            val height = Array.fill(colLength)(0)
            val left = Array.fill(colLength)(0)
            val right = Array.fill(colLength)(colLength)
            var area = 0
    
            for(i <- 0 to rowLength-1){
                var curLeft  = 0
                var curRight = colLength
    
                //height
                for(j <- 0 to colLength-1){
                    if(matrix(i)(j) == '1') height(j) += 1
                    else height(j) = 0
                }
    
                //left
                for(j <- 0 to colLength-1){
                    if(matrix(i)(j) == '1') left(j) = Math.max(left(j), curLeft)
                    else{
                        //left(j)设置为0,不影响面积计算,即height == 0
    					//设置为0 不影响后续max计算
                        left(j) = 0
                        curLeft = j + 1
                    }
                }
    
                //right
                for(j <- (0 to colLength-1).reverse){
                    if(matrix(i)(j) == '1') right(j) = Math.min(right(j), curRight)
                    else{
                         //right(j)设置为colLength,不影响面积计算,即height == 0
    					//设置为colLength 不影响后续min计算
                        right(j) = colLength
                        curRight = j
                    }
                }
    
                //area
                for(j <- 0 to colLength-1) area = Math.max(area, height(j)*(right(j) - left(j)))
            }
            return area
        }    
    }
    
  • 相关阅读:
    优化tomcat——jvm
    深入理解jvm
    Too many open files
    Ubuntu 18.04 chrome安装
    Ubuntu 对比度调节
    SSH 开启,安装
    Ubuntu的Gnome美化
    snap占用/dev/loop0-/dev/loop11占用100%
    C题——Halting Problem(补题)
    H:有趣的试剂(1317)
  • 原文地址:https://www.cnblogs.com/ganshuoos/p/13386840.html
Copyright © 2011-2022 走看看