You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

JavaScript二维数组fill方法赋值异常的原因咨询

二维数组赋值异常的原因解析

问题背景

想要创建一个按整数顺序填充的3×3二维数组,写出如下代码后实际输出不符合预期,同时疑惑new Array(3)为何不会引发引用错误:

代码示例

let length = 3
let arrMatrix = (new Array(3)).fill(Array(3));
arrMatrix.fill((new Array(3)).fill(0));
var sum = 0;
for(let i=0; i<length; i++) {
    for(let j=0; j<length; j++) {
        arrMatrix[i][j] = sum;
        sum += 1;
    }
}
console.log(arrMatrix);

实际输出

[ [ 6, 7, 8 ], [ 6, 7, 8 ], [ 6, 7, 8 ] ]

期望输出

[ [ 0, 1, 2 ], [ 3, 4, 5 ], [ 6, 7, 8 ] ]

问题原因

1. fill方法的引用类型共享问题

Array.prototype.fill()填充引用类型(比如数组)时,只会把该对象的内存地址复制到数组的每个位置,而非创建新的独立对象。

你的代码中,第二次调用arrMatrix.fill((new Array(3)).fill(0))时,(new Array(3)).fill(0)仅创建了一个数组对象,fill把这个数组的引用赋值给了arrMatrix的三个元素——也就是说,arrMatrix[0]、arrMatrix[1]、arrMatrix[2]指向的是同一个数组。

循环赋值时,你每次修改的都是这个共享数组的对应位置,最后一轮循环(i=2)将数组修改为[6,7,8],所以最终三个位置显示的都是这个结果。

2. new Array(3)为何不报错

new Array(3)是合法的JavaScript语法,它会创建一个长度为3的稀疏数组(数组本身是有效的对象,只是内部未初始化元素),因此可以正常调用fill方法,不会触发引用错误。

正确实现方式

要让二维数组的每个子数组都是独立对象,可使用map方法生成:

let length = 3;
// 先填充undefined,再通过map生成独立子数组
let arrMatrix = new Array(length).fill().map(() => new Array(length).fill(0));
var sum = 0;
for(let i=0; i<length; i++) {
    for(let j=0; j<length; j++) {
        arrMatrix[i][j] = sum;
        sum += 1;
    }
}
console.log(arrMatrix);

或更简洁的写法,直接在生成阶段填充序列:

let length = 3;
let arrMatrix = Array.from({ length }, (_, i) => 
    Array.from({ length }, (_, j) => i * length + j)
);
console.log(arrMatrix);

内容的提问来源于stack exchange,提问作者DrEarnest

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.22 10:52:23