Submatrix Sum

Given an integer matrix, find a submatrix where the sum of numbers is zero. Your code should return the coordinate of the left-up and right-down number.

Example

Given matrix

[
  [1 ,5 ,7],
  [3 ,7 ,-8],
  [4 ,-8 ,9],
]

return [(1,1), (2,2)]

分析:

本质上还是subarray sum. 因为对于要找的那个submatrix, 一定在0 和 matrix.length 之间。假设那个submatrix的上下row分别为i 和 j,那么我们可以把从i到j的那部分矩阵从上到下加起来,这样组成了一个一维数组,然后用Subarray Sum的方法解就可以了。

 1 public class Solution {
 2     /**
 3      * @param matrix an integer matrix
 4      * @return the coordinate of the left-up and right-down number
 5      */
 6     public int[][] submatrixSum(int[][] matrix) {
 7         int[][] res = new int[2][2];
 8         if (matrix == null || matrix.length == 0 || matrix[0].length == 0) return res;
 9         
10         int m = matrix.length;
11         int n = matrix[0].length;
12         // sum from 0,0 to i, j
13         int[][] sum = new int[m + 1][n + 1];
14         
15         for (int i = 1; i < sum.length; i++) {
16             for (int j = 1; j < sum[0].length; j++) {
17                 sum[i][j] = matrix[i - 1][j - 1] + sum[i - 1][j] + sum[i][j - 1] - sum[i - 1][j - 1];
18             }
19         }
20         //如果那个为0的矩阵在row i 和 j,那么我们可以把从i到j的那部分矩阵从上到下加起来,这样组成了一个一维数组,然后用Subarray Sum的方法解就可以了
22 
23         for (int r1 = 0; r1 < m; r1++) {
24             for (int r2 = r1 + 1; r2 <= m; r2++) {
25                 Map<Integer, Integer> map = new HashMap<Integer, Integer>();
26                 for (int j = 0; j <= n; j++) {
27                     int zeroToJSum = sum[r2][j] - sum[r1][j];
28                     if (map.containsKey(zeroToJSum)) {
29                         res[0][0] = r1;
30                         res[0][1] = map.get(zeroToJSum);
31                         res[1][0] = r2 - 1;
32                         res[1][1] = j - 1;
33                         return res;
34                     } else {
35                         map.put(zeroToJSum, j);
36                     }
37                 }
38             }
39         }
40         return res;
41     }
42 }

下面的代码思路和上面一样,只是实现不一样。

 1 public class Solution {
 2     /**
 3      * @param matrix an integer matrix
 4      * @return the coordinate of the left-up and right-down number
 5      */
 6     public int[][] submatrixSum(int[][] matrix) {
 7         int[][] res = new int[2][2];
 8         if (matrix == null || matrix.length == 0 || matrix[0].length == 0) return res;
 9         
10         int m = matrix.length;
11         int n = matrix[0].length;
12         int[][] sum = new int[m][n];
13         
14         for (int i = 0; i < m; i++) {
15             for (int j = 0; j < n; j++) {
16                 if (i == 0) {
17                     sum[i][j] = matrix[i][j];
18                 } else {
19                     sum[i][j] = matrix[i][j] + sum[i - 1][j];
20                 }
21             }
22         }
23         
24         for (int r1 = 0; r1 < m; r1++) {
25             for (int r2 = r1; r2 < m; r2++) {
26                 res = check(sum, r1, r2);
27                 if (res != null) return res;
28             }
29         }
30         return res;
31     }
32     
33     private int[][] check(int[][] sum, int r1, int r2) {
34         Map<Integer, Integer> map = new HashMap<Integer, Integer>();
35         
36         map.put(0, -1);
37         int zeroToJSum = 0;
38         for (int j = 0; j < sum[0].length; j++) {
39             if (r1 == 0) {
40                 zeroToJSum = sum[r2][j] + zeroToJSum;
41             } else {
42                 zeroToJSum = sum[r2][j] - sum[r1 - 1][j] + zeroToJSum;
43             }
44             
45             if (map.containsKey(zeroToJSum)) {
46                 int[][] res = new int[2][2];
47                 res[0][0] = r1;
48                 res[0][1] = map.get(zeroToJSum) + 1;
49                 res[1][0] = r2;
50                 res[1][1] = j;
51                 return res;
52             } else {
53                 map.put(zeroToJSum, j);
54             }
55         }
56         return null;
57     }
58 }

Reference:

https://segmentfault.com/a/1190000004878083

转载于:https://www.cnblogs.com/beiyeqingteng/p/5686895.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值