|
| 1 | +/* |
| 2 | +solution 1. 재귀 호출 |
| 3 | +Time Complexity: O(m * n * (m + n)) |
| 4 | +Space Complexity: O(m * n) |
| 5 | +처음에는 공간 복잡도를 O(1)이라고 생각했으나, 검색해보니 함수 호출 스택도 공간 복잡도 계산에 포함시켜야만 한다. 따라서 이 방법은 공간 복잡도 제한을 만족시키지 못한다. |
| 6 | +(참고 : https://en.wikipedia.org/wiki/In-place_algorithm), |
| 7 | +
|
| 8 | +
|
| 9 | +solution 2. bit manipulation |
| 10 | +
|
| 11 | +long 변수를 선언해서, 각 bit에 x번째 row(혹은 col)를 0으로 바꿀지 여부를 기록한다. |
| 12 | +(m + n) / 64 개의 변수를 써서 가능하긴 하지만, 64라는 factor가 다소 클 뿐, 결국 공간 복잡도는 O(m + n). |
| 13 | +
|
| 14 | +
|
| 15 | +solution 3. matrix 내에 안 쓰이는 값 찾기 (probabilistic 접근) |
| 16 | +int32 범위 내에서, 쓰이는 값보다는 안 쓰이는 값의 갯수가 압도적으로 많다.(99.999%+) |
| 17 | +
|
| 18 | +int 범위 내의 숫자를 랜덤하게 뽑는다면, 그리고 이 행위를 10번만 반복한다면 |
| 19 | +O(m * n) 시간에 상당히 높은 확률로 안 쓰이는 값(x라고 하자)을 찾을 수 있다. |
| 20 | +(틀릴 확률은 10^(-50) 정도.) |
| 21 | +matrix의 모든 원소를 순회하며, 값이 0이라면 같은 row/col에 존재하는 모든 원소(또다른 0은 제외)를 위에서 찾은 x로 바꾼 뒤에, 마지막에 한번에 모든 x를 0으로 바꾸는 식으로 풀 수 있다. |
| 22 | +
|
| 23 | +그러나 이 접근법의 확률은 문제의 제한 조건 m, n 범위 하에서 계산한 것이라는 한계가 있다. |
| 24 | +m, n이 꽤나 커진다면 맞출 확률이 낮아지고, 극단적으로 m = n = 2^16 = 65,536 이상이 되면, 쓸 수 없는 방법이기도 하다. |
| 25 | +
|
| 26 | +
|
| 27 | +solution 4. in-place marking |
| 28 | +(AlgoDale 풀이를 참고함) |
| 29 | +Time Complexity: O(m * n) |
| 30 | +Space Complexity: O(1) |
| 31 | +
|
| 32 | +*/ |
| 33 | +class Solution { |
| 34 | + |
| 35 | + // solution 4. in-place marking |
| 36 | + public void setZeroes(int[][] matrix) { |
| 37 | + int m = matrix.length; |
| 38 | + int n = matrix[0].length; |
| 39 | + |
| 40 | + boolean should0thColumnBeZero = false; |
| 41 | + for (int i = 0; i < m; i++) { |
| 42 | + if (matrix[i][0] == 0) { |
| 43 | + should0thColumnBeZero = true; |
| 44 | + } |
| 45 | + } |
| 46 | + |
| 47 | + for (int i = 0; i < m; i++) { |
| 48 | + for (int j = 1; j < n; j++) { |
| 49 | + if (matrix[i][j] == 0) { |
| 50 | + matrix[i][0] = matrix[0][j] = 0; |
| 51 | + } |
| 52 | + } |
| 53 | + } |
| 54 | + |
| 55 | + for (int i = 1; i < m; i++) { |
| 56 | + if (matrix[i][0] == 0) { |
| 57 | + for (int j = 1; j < n; j++) { |
| 58 | + matrix[i][j] = 0; |
| 59 | + } |
| 60 | + } |
| 61 | + } |
| 62 | + for (int i = 1; i < n; i++) { |
| 63 | + if (matrix[0][i] == 0) { |
| 64 | + for (int j = 0; j < m; j++) { |
| 65 | + matrix[j][i] = 0; |
| 66 | + } |
| 67 | + } |
| 68 | + } |
| 69 | + if (matrix[0][0] == 0) { |
| 70 | + for (int i = 0; i < n; i++) { |
| 71 | + matrix[0][i] = 0; |
| 72 | + } |
| 73 | + } |
| 74 | + if (should0thColumnBeZero) { |
| 75 | + for (int i = 0; i < m; i++) { |
| 76 | + matrix[i][0] = 0; |
| 77 | + } |
| 78 | + } |
| 79 | + } |
| 80 | + |
| 81 | + /* solution 1. 재귀 호출 |
| 82 | + public void setZeroes(int[][] matrix) { |
| 83 | + dfs(matrix, 0, 0); |
| 84 | + } |
| 85 | +
|
| 86 | + public void dfs(int[][] matrix, int sr, int sc) { |
| 87 | + int m = matrix.length; |
| 88 | + int n = matrix[0].length; |
| 89 | + for (int r = sr; r < m; r++) { |
| 90 | + boolean found = false; |
| 91 | + for (int c = (r == sr) ? sc : 0; c < n; c++) { |
| 92 | + if (matrix[r][c] != 0) { |
| 93 | + continue; |
| 94 | + } |
| 95 | +
|
| 96 | + int nr = (c == n) ? (r + 1) : r; |
| 97 | + int nc = (c == n) ? 0 : c + 1; |
| 98 | + dfs(matrix, nr, nc); |
| 99 | + setRowAndColumnZeroes(matrix, r, c); |
| 100 | + |
| 101 | + found = true; |
| 102 | + break; |
| 103 | + } |
| 104 | + if (found) { |
| 105 | + break; |
| 106 | + } |
| 107 | + } |
| 108 | + } |
| 109 | +
|
| 110 | + public void setRowAndColumnZeroes(int[][] matrix, int r, int c) { |
| 111 | + int m = matrix.length; |
| 112 | + int n = matrix[0].length; |
| 113 | + for (int i = 0; i < n; i++) { |
| 114 | + matrix[r][i] = 0; |
| 115 | + } |
| 116 | + for (int i = 0; i < m; i++) { |
| 117 | + matrix[i][c] = 0; |
| 118 | + } |
| 119 | + } |
| 120 | + */ |
| 121 | +} |
0 commit comments