矩阵的所有行中的值更改

时间:2018-05-12 20:58:37

标签: javascript arrays node.js

所以我决定签出 Array.prototype.fill()方法,因此我创建了一个简单的函数,它应该返回一个填充了空值或用户选择值的矩阵。 / p>

我的代码看起来像这样:

function Matrix(x,y,value){
    if(value === undefined){
        value = null;
    }

    let arr = new Array(y);
    arr.fill(row());
    return arr;

    function row(){
        let subarr = new Array(x);
        subarr.fill(value);
        return subarr;
    }
}

乍一看,效果非常好。当我试图重新分配其中一个值时,问题就出现了。

let arr = Matrix(5,5);

arr[2][2] = 'marked as duplicate';
console.log(arr);

当然,我预计只会改变其中一个值,但我得到的输出是:

[ [ null, null, 'marked as duplicate', null, null, null, null ],
  [ null, null, 'marked as duplicate', null, null, null, null ],
  [ null, null, 'marked as duplicate', null, null, null, null ],
  [ null, null, 'marked as duplicate', null, null, null, null ],
  [ null, null, 'marked as duplicate', null, null, null, null ] ]

有人可以向我解释为什么会发生这种情况吗?

感谢。

2 个答案:

答案 0 :(得分:1)

来自MDN对Array.prototype.fill()的描述(强调我的):

  

fill()方法从一开始就填充数组的所有元素   指向具有静态值的结束索引。

在这一行:

arr.fill(row());

Array.fill()不会为每个元素调用row()方法一次;它将调用一次,并将一个结果分配给数组的每个元素。

答案 1 :(得分:0)

正如@mate所说,引用 MDN

  

fill()方法使用静态值将数组的所有元素从起始索引填充到结束索引。

因此,您的"y"数组从开始到结束都包含相同的"x"数组,因为row()仅在使用结果数组填充初始数组之前计算一次

在您的示例中尝试console.log(arr[0] === arr[1]);会记录true,但您希望它能够记录false

以下是您问题的解决方案:

function Matrix(x, y, value) {
  if (!value) value = null;

  let arr = new Array(y);
  arr.fill(value);       // Fill with something just to be able to iterate
  return arr.map(row);   // build a new array with map() calling row() at
                             // each iteration
  function row() {
    let subArr = new Array(x);
    subArr.fill(value);
    return subArr;       // Return the sub-array to collect it with map()
  }
}

let arr = Matrix(5, 5);

arr[2][2] = 'marked as duplicate';
console.log(arr[0] === arr[1]);    // → Will log false
console.log(arr);        // Try the snippet below to see

摘录:  



function Matrix(x, y, value) {
  if (!value) value = null;

  let arr = new Array(y);
  arr.fill(value);
  return arr.map(row);

  function row() {
    let subArr = new Array(x);
    subArr.fill(value);
    return subArr;
  }
}

let arr = Matrix(5, 5);

arr[2][2] = 'marked as duplicate';
console.log(arr[0] === arr[1]);
console.log(arr);