算法记录
LeetCode 题目:
给定一个二维矩阵 matrix,以下类型的多个请求:
计算其子矩形范围内元素的总和,该子矩阵的左上角为(row1, col1) ,右下角为 (row2, col2) 。
- NumMatrix() 给定整数矩阵 matrix 进行初始化
- int sumRegion() 返回左上角 (row1, col1) 、右下角 (row2, col2) 所描述的子矩阵的元素总和 。
说明
一、题目
输入:
["NumMatrix","sumRegion","sumRegion","sumRegion"]
[[[[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]]],[2,1,4,3],[1,1,2,2],[1,2,2,4]]
输出:
[null, 8, 11, 12]
解释:
NumMatrix numMatrix = new NumMatrix([[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]]);
numMatrix.sumRegion(2, 1, 4, 3); // return 8 (红色矩形框的元素总和)
numMatrix.sumRegion(1, 1, 2, 2); // return 11 (绿色矩形框的元素总和)
numMatrix.sumRegion(1, 2, 2, 4); // return 12 (蓝色矩形框的元素总和)
二、分析
- 题目不难,就是一个前缀和的二维应用,但是需要注意条件的划分,因为在计算的过程中会出现多计算的现象,需要进行规避。
- 不画图不好解释,直接看代码可能还好理解一点。
class NumMatrix {
private int[][] sums;
private Integer m;
private Integer n;
public NumMatrix(int[][] matrix) {
sums = matrix;
m = matrix.length - 1;
n = matrix[0].length - 1;
for(int i = 0; i <= m; i++) {
for(int j = 0; j <= n; j++) {
if(i - 1 >= 0) sums[i][j] += sums[i - 1][j];
if(j - 1 >= 0) sums[i][j] += sums[i][j - 1];
if(i - 1 >= 0 && j - 1 >= 0) {
sums[i][j] -= sums[i - 1][j - 1];
}
}
}
}
public int sumRegion(int row1, int col1, int row2, int col2) {
int ret = sums[row2][col2];
if(row1 - 1 >= 0) ret -= sums[row1 - 1][col2];
if(col1 - 1 >= 0) ret -= sums[row2][col1 - 1];
if(col1 - 1 >= 0 && row1 - 1 >= 0) ret += sums[row1 - 1][col1 - 1];
return ret;
}
}
总结
前缀和的二维应用。