前言
今天刷leetcode 542. 01 矩阵,在创建二维数组时遇到了坑,跟大家分享一下。
我的错误实现
实现一个m*n的二维数据,看我的实现。
const seen = new Array(m).fill(new Array(n).fill(false))并未觉得不妥,愉快地coding。但是后面却遇到了大问题。
这里简单点,先用 2 x 2 的最小化示例重现下。
const mat = [
[0, 1],
[2, 3]
]
const m = mat.length, n = mat[0].length
const seen = new Array(m).fill(new Array(n).fill(false))
console.log(seen) // [ [ false, false ], [ false, false ] ]
for (let i = 0; i < m; i++) {
for (let j = 0; j < n; j++) {
if (mat[i][j] === 0) {
seen[i][j] = true
}
}
}
console.log(seen) // [ [ true, false ], [ true, false ] ]
一看这打印结果,显然是预料之外的。为啥会这样呢?
因为我们fill的时候,直接把一个数组填充进去了,内存地址相同的那种!!!
所以前面的结果会被后面的结果覆盖,最终的效果是每一行都是一样的结果。
如何改正呢?
正确的写法
千万记得用map()
- const seen = new Array(m).fill(new Array(n).fill(false))
+ const seen = new Array(m).fill().map(() => new Array(n).fill(false))
千万别偷懒,那是重大BUG!
const seen = new Array(m).fill().map(() => new Array(n).fill(false))
leetcode 通过的代码
最终通过的代码!
/**
* @param {number[][]} mat
* @return {number[][]}
*/
var updateMatrix = function (mat) {
// 有一个“超级零”的概念,连接所有的0
const m = mat.length, n = mat[0].length
// dist: 最终的结果,seen 记录访问数组,queue 广度优先队列
const dist = new Array(m).fill().map(()=>new Array(n).fill(0))
const seen = new Array(m).fill().map(()=>new Array(n).fill(false))
const queue = []
for (let i = 0; i < m; i++) {
for (let j = 0; j < n; j++) {
if (mat[i][j] === 0) {
queue.push([i, j])
seen[i][j] = true
}
}
}
const dirs = [[-1, 0], [1, 0], [0, -1], [0, 1]]
while (queue.length) {
const [x, y] = queue.shift()
for (const [dx, dy] of dirs) {
const [r, c] = [x + dx, y + dy]
if (r >= 0 && r < m && c >= 0 && c < n && !seen[r][c]) {
dist[r][c] = dist[x][y] + 1
queue.push([r,c])
seen[r][c] = true
}
}
}
return dist
};