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

Unexpected behavior using Array Map on an Array Initialized with Array Fill

本文关键字:数组 意外 映射 填充 初始化      更新时间:2023-09-26

由于与Array.prototype.map一起使用时意外输出,我在使用新Array.prototype.fill方法时遇到了问题。例如:

// 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 转换将 ES6 代码转换为 ES5。

您的代码等效于:

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));
}