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

上图子矩阵左上角 (row1, col1) = (2, 1) ,右下角(row2, col2) = (4, 3),该子矩形内元素的总和为 8。
示例 1:
给定 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 方法。
你可以假设 row1 ≤ row2 且 col1 ≤ col2 。
解题思路
做过昨天的每日一题的朋友做这道题应该很快就有思路了,只不过是把一维数组转为二维数组。
子矩阵左上坐标为(i,j),右下坐标为(x,y),其求和相当于i行到x行,每一行上索引为j到y的元素和,再求和。
所以在初始化时可以参照昨天的题目,每行元素存前n项和。
在每行上,因为数组索引i到索引j的和,等于a[i]+a[i+1]+…+a[j],也即等于a[0]+…+a[j] - (a[0]+…+a[i-1])
也就是前j项和减去前i-1项和,所以我们在构造NumArray可以存前n项和,根据上面的公式显然当i=0时需要特殊讨论,
当i=0时,就是前j项和,所以可以初始化数组sum[0]=0,sum[i+1] = sum[i] + a[i],即第i+1项存数组a的前i项和,这样当我们要求索引i到索引j的和时,也就是求索引j项和减去索引i-1项和,换成sum数组的索引就是sum[j+1]-sum[i-1+1],即sum[j+1] - sum[i],这样只需要构造类时遍历一次,之后直接做一个减法即可。
再将求得的每行的元素和累加,即为答案。
当然还有存二维数组和的解法,可以去leetcode上看下。
代码
type NumMatrix struct {
sumMatrix [][]int
}
func Constructor(matrix [][]int) NumMatrix {
if len(matrix) == 0 {
return NumMatrix{
nil,
}
}
sumMatrix := make([][]int, len(matrix))
for i, _ := range sumMatrix {
sumMatrix[i] = make([]int, len(matrix[0])+1)
}
for i := 0; i < len(sumMatrix); i++ {
sumMatrix[i][0] = 0
}
for i := 0; i < len(sumMatrix); i++ {
for j := 1; j < len(sumMatrix[i]); j++ {
sumMatrix[i][j] = sumMatrix[i][j-1] + matrix[i][j-1]
}
}
return NumMatrix{sumMatrix: sumMatrix}
}
func (this *NumMatrix) SumRegion(row1 int, col1 int, row2 int, col2 int) int {
sum :=0
for i := 0;i<=(row2-row1);i++{
sum = sum+this.sumMatrix[row1+i][col2+1]-this.sumMatrix[row1+i][col1]
}
return sum
}
本文介绍LeetCode 304题的解决方案,利用Go语言实现二维矩阵子区域求和的功能。通过预处理存储每行的前缀和,快速响应多次查询请求。
627

被折叠的 条评论
为什么被折叠?



