[Leetcode Daily] 304. 二维区域和检索 - 矩阵不可变

Description

给定一个二维矩阵,计算其子矩形范围内元素的总和,该子矩阵的左上角为 (row1, col1) ,右下角为 (row2, col2) 。
示例:

给定 matrix = [
[3, 0, 1, 4, 2],
[5, 6, 3, 2, 1],
[1, 2, 0, 1, 5],
[4, 1, 0, 1, 7],
[1, 0, 3, 0, 5]
]

sumRegion(2, 1, 4, 3) -> 8
sumRegion(1, 1, 2, 2) -> 11
sumRegion(1, 2, 2, 4) -> 12

思路

昨天动态规划的升级版。依然考虑打表。和昨天不同,求和矩阵有四个坐标。设sumRegion(a,b,c,d)=f((a,b),(c,d)),a≤c,b≤dsumRegion(a,b,c,d)=f((a,b),(c,d)),a\leq c,b\leq dsumRegion(a,b,c,d)=f((a,b),(c,d)),ac,bd,注意到如下状态转移公式:
f((a,b),(c,d))=f((0,0),(c,d))−f((0,0),(a,d))−f((0,0),(c,b))+f((0,0),(a,b)) f((a,b),(c,d))=f((0,0),(c,d))-f((0,0),(a,d))-f((0,0),(c,b))+f((0,0),(a,b)) f((a,b),(c,d))=f((0,0),(c,d))f((0,0),(a,d))f((0,0),(c,b))+f((0,0),(a,b))
也就是把四个参数简化为两个参数,减少了打表的空间。

接下来考虑怎么打表。设f((0,0),(a,b))=g(a,b)f((0,0),(a,b))=g(a,b)f((0,0),(a,b))=g(a,b),注意到状态转移公式:
g(0,0)=Matrix[0][0]g(a,b+1)=g(a,b)+∑j=0aMatrix[j][b+1] g(0,0)=Matrix[0][0]\\ g(a,b+1)=g(a,b)+\sum_{j=0}^{a}Matrix[j][b+1] g(0,0)=Matrix[0][0]g(a,b+1)=g(a,b)+j=0aMatrix[j][b+1]
sum部分可以考虑打表进行进一步空间换时间?
总之这个题就是这样,顺着公式写就好了。
下面是官方题解:

代码

class NumMatrix:

    def __init__(self, matrix: List[List[int]]):
        m, n = len(matrix), (len(matrix[0]) if matrix else 0)
        self.sums = [[0] * (n + 1) for _ in range(m + 1)]
        _sums = self.sums

        for i in range(m):
            for j in range(n):
                _sums[i + 1][j + 1] = _sums[i][j + 1] + _sums[i + 1][j] - _sums[i][j] + matrix[i][j]

    def sumRegion(self, row1: int, col1: int, row2: int, col2: int) -> int:
        _sums = self.sums

        return _sums[row2 + 1][col2 + 1] - _sums[row1][col2 + 1] - _sums[row2 + 1][col1] + _sums[row1][col1]

打卡。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值