73.矩阵置零
题目
给定一个 m x n 的矩阵,如果一个元素为 0,则将其所在行和列的所有元素都设为 0。请使用原地算法。
示例 1:
输入:
[
[1,1,1],
[1,0,1],
[1,1,1]
]
输出:
[
[1,0,1],
[0,0,0],
[1,0,1]
]
方法一
用两个set分别记录需要置0的行和需要置0的列。第一次遍历矩阵时,若发现一个元素为0,则将其行和列值分别加入到两个set中。第二次遍历矩阵时,将行set中的行全部置0,将列set中的列全部置0。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
| public void setZeroes(int[][] matrix) { if(matrix == null || matrix.length == 0) return; int m = matrix.length, n = matrix[0].length; Set<Integer> row = new HashSet<Integer>(); Set<Integer> col = new HashSet<Integer>(); for(int i = 0; i < m; i++){ for(int j = 0; j < n; j++){ if(matrix[i][j] == 0){ row.add(i); col.add(j); } } } for(int i : row){ for(int j = 0; j < n; j++) matrix[i][j] = 0; } for(int j : col){ for(int i = 0; i < m; i++) matrix[i][j] = 0; } }
|
- 时间复杂度:O(m * n)
- 空间复杂度:O(m + n) 最坏情况是矩阵中全部元素为0的情况,这时两个set的大小分别为m和n。
方法二
思路:不用额外空间,让首行和首列记录某列和某行是否有0
算法步骤:
- 首先用两个布尔类型变量firstRow和firstCol分别记录矩阵的首行和首列中是否有0
- 遍历除首行和首列外的所有元素,若元素matrix[i][j]为0,则将它对应的首行和首列中的元素matrix[i][0]和matrix[0][j]置为0,意为此行和列后续需要被置0(由于修改后首行和首列是否有0的信息会被破坏掉,因此需要有之前的步骤一)
- 遍历首行和首列,若发现首行中有元素为0,则将此元素所处的列全部置0,若发现首列中有元素为0,则将此元素所处的行全部置0。
- 根据步骤一的布尔类型变量firstRow和firstCol来判断首行和首列是否需要被置0。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46
| public void setZeroes(int[][] matrix) { if(matrix == null || matrix.length == 0) return; int m = matrix.length, n = matrix[0].length; boolean firstRow = false, firstCol = false; for(int i = 0; i < m; i++){ if(matrix[i][0] == 0) firstCol = true; } for(int j = 0; j < n; j++){ if(matrix[0][j] == 0) firstRow = true; } for(int i = 1; i < m; i++){ for(int j = 1; j < n; j++){ if(matrix[i][j] == 0){ matrix[i][0] = 0; matrix[0][j] = 0; } } } for(int i = 1; i < m; i++){ if(matrix[i][0] == 0){ for(int j = 0; j < n; j++) matrix[i][j] = 0; } } for(int j = 1; j < n; j++){ if(matrix[0][j] == 0){ for(int i = 0; i < m; i++) matrix[i][j] = 0; } } if(firstRow){ for(int j = 0; j < n; j++) matrix[0][j] = 0; } if(firstCol){ for(int i = 0; i < m; i++) matrix[i][0] = 0; } }
|
- 时间复杂度:O(m * n)
- 空间复杂度:O(1)