2016-12-06 57 views
2

有人能向我解釋爲什麼以下的Javascript控制檯發生(節點7.2.0):例如,在JavaScript數組差異不同初始化方法

陣列I具有比例如II和III

不同的行爲實例我

> var x = new Array(3).fill(new Array(2).fill(0)) 
> x 
[ [ 0, 0 ], [ 0, 0 ], [ 0, 0 ] ] 
> x[0][0] = 1; 
> x 
[ [ 1, 0 ], [ 1, 0 ], [ 1, 0 ] ] 

例Ⅱ

> var y = [...new Array(3)].map(()=>{return [...new Array(2)].map(()=>0)}) 
> y 
> [ [ 0, 0 ], [ 0, 0 ], [ 0, 0 ] ] 
> y[0][0] = 1 
> [ [ 1, 0 ], [ 0, 0 ], [ 0, 0 ] ] 

實施例III

> var y = [] 
> y.push([ 0, 0 ]) 
> y.push([ 0, 0 ]) 
> y.push([ 0, 0 ]) 
> y 
> [ [ 0, 0 ], [ 0, 0 ], [ 0, 0 ] ] 
> y[0][0] = 1 
> [ [ 1, 0 ], [ 0, 0 ], [ 0, 0 ] ] 

看來不同的方式來初始化數組將使陣列的不同的行爲。我很困惑,並提前感謝你。

回答

7

array.fill()返回已修改的數組,因此您要用對同一數組的多個引用填充數組。這就是爲什麼當你在一個地方修改它時,它會自動顯示在其他地方。

第一個例子是相當於做類似:

var arr = [ 0, 0 ]; 
var x = [ arr, arr, arr ]; 
+0

我不這麼認爲,我特別使用了new運算符來爲fill函數創建一個新數組,以避免使用相同的引用。 – weiway

+4

'new Array()'創建一個*數組* *。 array.fill()不會創建副本,它只是將數組元素分配給傳遞給它的任何內容(在本例中爲單個數組)。 – mscdex

0

的原因不同的是,在JS,對象(包括數組)不會被複制,它們被鏈接。在例子I中,你用一個數組填充數組。

> var x = new Array(3).fill(new Array(2).fill(0)) 
// You have filled x with three links to the same array 
> x 
[ [ 0, 0 ], [ 0, 0 ], [ 0, 0 ] ] 
> x[0][0] = 1; 
// You have now modified the actual array, this change is reflected in all the links to it. 
> x 
[ [ 1, 0 ], [ 1, 0 ], [ 1, 0 ] ] 

你在做什麼是一樣的做:

var a = [ 0, 0 ] 
var x = [ a, a, a ] 

OR

var a = [ 0, 0 ] 
var x = [] 
x.push(a) 
x.push(a) 
x.push(a) 

BTW,使用new Array()一般是不好的做法。數組文字語法沒有任何好處。此外,使用new Array(n)會在您的陣列中產生「空插槽」,這是非常奇怪的,如果您未填滿所有插槽,可能會在程序中導致問題。