在用数组填充初始化的数组上使用数组映射的意外行为

IT技术 javascript ecmascript-6
2021-02-07 07:33:02

Array.prototype.fill由于在将新方法与Array.prototype.map. 例如:

// Initialize our n x n matrix and fill with 0's
let M = Array(3).fill(Array(3).fill(0));

M.map(function (row, i) {
    row[i] = i;
    return row;
}); //=> [[0, 1, 2], [0, 1, 2], [0, 1, 2]]

在上面的示例中,我希望输出与下面的示例相同:

let  M = [[0, 0, 0], [0, 0, 0], [0, 0, 0]];

M.map(function (row, i) {
    row[i] = i;
    return row;
}); //=> [[0, 0, 0], [0, 1, 0], [0, 0, 2]]

然而事实并非如此。出于某种原因,第一个示例中返回的结果将用作下一次迭代中的行值。任何想法为什么会发生这种情况?我正在使用 6to5ify 转换为 browserify 将 ES6 代码转换为 ES5。

1个回答

您的代码相当于:

let inner = Array(3).fill(0);
let M = Array(3).fill(inner);

当您传递inner给 时.fill(),它不会复制它,该M数组包含对同一数组的 3 个引用。所以你对一个元素所做的任何事情都会M发生在他们身上。

您需要为每个元素创建新数组M

let M = [];
for (var i = 0; i < 3; i++) {
    M.push(Array(3).fill(0));
}