讓我們說我有一個數組,var animals = ["dog","cat","rat"];
通過參考解決方法的JavaScript通
然後我定義var pets = animals;
然後我打電話pets.shift();
現在因爲JavaScript是通過按引用數組,如果我現在撥打animals
,我會得到["cat","rat"]
。
我的問題:有沒有辦法解決這個問題,如果我稍後想以未修改的形式使用animals
?
讓我們說我有一個數組,var animals = ["dog","cat","rat"];
通過參考解決方法的JavaScript通
然後我定義var pets = animals;
然後我打電話pets.shift();
現在因爲JavaScript是通過按引用數組,如果我現在撥打animals
,我會得到["cat","rat"]
。
我的問題:有沒有辦法解決這個問題,如果我稍後想以未修改的形式使用animals
?
關於術語的說明:JavaScript是從不pass-by-reference(不管你聽到有多少人說這是)。當你寫了一行:
var pets = animals;
你分配的animals
的值到pets
。分配的值是對數組的引用,因此現在兩個變量都將指向內存中的同一對象。 (注意:這有些迂腐,但它也有正確的好處。)
如果你想讓這兩個變量引用兩個不同的數組,那麼你需要創建一個原始副本數組並將其分配給pets
。要做到這一點在JavaScript中最常見的方式是採取的事實,即一些陣列方法(如slice
或concat
)創建數組的副本上,他們是所謂:
var pets = animals.concat();
證明的/平等:
var arr = [];
arr1 = arr;
console.log(arr1 === arr); // true
console.log(arr1 === arr.concat()) // false
當然,您也可以自己進行復制:
function copy(arr) {
var i, len = arr.length, arr1 = new Array(len);
for (i = 0; i < len; i += 1) {
arr1[i] = arr[i];
}
return arr1;
}
事實上,this is probably a lot faster並應被視爲˚F或非常大的陣列。 (在大多數情況下,只需做最可讀的操作。)
請注意,每種方法都會創建一個淺副本的原始數組。如果數組持有對其他對象的引用,那麼這些引用將被複制到新數組中(即,原始數組和新數組都將引用相同的對象)。另一方面,字符串和數字直接複製到新數組中。
你要克隆的陣列,它與
var savedAnimals = animals.slice();
請注意,這不是一個深克隆完成:它不保護元件內部對修改(如果他們不是字符串) 。
是的,這是有效的。謝謝!任何其他策略? –
這是最好的,這是標準的。 –
感謝您的徹底解答。一個微妙的區別,我會花一些時間來包裝我的大腦。 –
所以 - 如果複製數組包含和對象,然後修改,我可以有同樣的問題。 –
是的。你可能想看看這裏:http://stackoverflow.com/questions/122102/most-efficient-way-to-clone-an-object –