【Python刷题】LeetCode 1727 重新排列后的最大子矩阵

题目链接:https://leetcode.cn/problems/largest-submatrix-with-rearrangements/

题目描述

给定一个二进制矩阵 matrix,我们可以任意重排列矩阵的列。要求找到矩阵中全为 1 的最大子矩阵,并返回其面积。
示例 1:

输入 :matrix = [[0,0,1],[1,1,1],[1,0,1]]
输出 :4
解释 :你可以按照上图方式重新排列矩阵的每一列。

最大的全 1 子矩阵是上图中加粗的部分,面积为 4 。

解题思路

这题让我们通过改变每一 的顺序,来构建一个尽可能大的全 1 矩形 ,而这个矩形到底在整个矩阵的哪个位置是无法确定的,但是我们只要把矩形的底边所在的行给固定,那么问题就变简单了。只需要遍历所有行然后把以该行作为底边时能够得到的所有矩形找到,总是选取最大的矩阵就行了。

因此可以用一个非常形象的方式来理解:把矩阵看成一排楼房 ,我们通过改变地基来要找出能构成的最大矩形连续房间面积。

我们可以把矩阵的每一行当作当前的地基每一列看作一栋楼 。数字 1 代表这一层有楼,数字 0 代表这一层是空的。因为题目允许我们任意重排列 ,就相当于我们可以自由调换这些楼的左右顺序 ,把它们从左到右、从高到低排列,遍历每一个楼,左边所有楼都比当前楼更高或一样高,所以从最左到当前位置,一定能画出一个完整矩形

整体思路非常直观:

  1. 遍历每一行,把它当作新的底边。
  2. 维护一个高度数组,记录每栋楼当前的总层数。
  3. 遇到 1 就把楼层加高一层,遇到 0 就直接把这栋楼坍塌为 0 层。
  4. 把所有楼按高度从高到低排序,从左往右依次计算能围成的最大矩形。
  5. 遍历过程中不断更新最大值,最后就是答案。

算法动图

代码实现

python 复制代码
class Solution:
    def largestSubmatrix(self, matrix: List[List[int]]) -> int:
        m,n=len(matrix),len(matrix[0])
        h=[0]*n#记录当前底边上的楼层的全部高度
        res=0
        for row in matrix:#遍历不同的底边
            for j in range(n):#遍历每栋楼楼
                h[j] = h[j]+1 if row[j] == 1 else 0#遇到1就扩建,遇到0就拆除
            sorted_h = sorted(h,reverse=True)#把楼层高度从高到低排列
            for i in range(0,n):#i从左到右遍历每栋楼,不停增加连续楼层的总宽度(i+1)
                res = max(res,sorted_h[i]*(i+1))#宽度乘当前楼高就是当前宽度能得到的最大面积,取最值
        return res

代码解释

  • m,n=len(matrix),len(matrix[0]):获取矩阵的行数和列数。
  • h=[0]*n:记录当前底边上,每一栋楼的楼层高度。
  • res=0:用来保存最终的最大面积。
  • for row in matrix:遍历每一行,把每一行当作一条新的底边。
  • for j in range(n):遍历每一栋楼。
  • h[j] = h[j]+1 if row[j] == 1 else 0:遇到 1 就扩建楼层,遇到 0 就直接拆除归零。
  • sorted_h = sorted(h,reverse=True):把所有楼按高度从高到低排列,因为列可以随便换顺序。
  • for i in range(0,n):从左到右一栋一栋看,连续的楼越来越多,宽度越来越大。
  • res = max(res,sorted_h[i]*(i+1)):当前宽度是 i+1,当前最矮的楼决定高度,相乘就是矩形面积,不断更新最大值。
  • 最后返回 res 就是全 1 最大子矩阵的面积。

复杂度分析

  • 时间复杂度:O(m * n log n)
    遍历每一行是 O(m),更新楼层高度 O(n),每次排序 O(n log n),整体为 O(m * n log n)。
  • 空间复杂度:O(n)
    只使用了一个一维数组记录楼层高度,额外空间很小。

总结

这道题最巧妙的地方,就是把二维矩阵的全 1 子矩形问题,转化成了楼层柱状图 问题。

再利用题目可以重排列的条件,直接排序贪心求解,思路清晰、代码简洁,是一道非常经典的贪心与矩阵结合的好题。

相关推荐
做怪小疯子2 小时前
蚂蚁暑期 319 笔试
算法·职场和发展
计算机安禾2 小时前
【C语言程序设计】第37篇:链表数据结构(一):单向链表的实现
c语言·开发语言·数据结构·c++·算法·链表·蓝桥杯
啊哦呃咦唔鱼2 小时前
LeetCode hot100-73 矩阵置零
算法
阿贵---2 小时前
C++构建缓存加速
开发语言·c++·算法
Queenie_Charlie3 小时前
最长回文子串 V2(Manacher算法)
c++·算法·manacher算法
Evand J3 小时前
【MATLAB复现RRT(快速随机树)算法】用于二维平面上的无人车路径规划与避障,含性能分析与可视化
算法·matlab·平面·无人车·rrt·避障
一招定胜负3 小时前
机器学习+深度学习经典算法面试复习指南
深度学习·算法·机器学习
皮卡狮3 小时前
高阶数据结构:AVL树
数据结构·算法
天若有情6733 小时前
通用个性化推荐核心架构思路:从视频到电商的跨场景落地实践
人工智能·算法·架构·推流·个性化推荐·猜你喜欢