const oldArr = [1,2,3];
const newArr = oldArr; // now oldArr points to the same place in memory
console.log(oldArr === newArr); // Points to the same place in memory thus is true
const copy = [1,2,3];
console.log(copy === newArr); // Doesn't point to the same place in memory and thus is false
const oldArr = [1,2,3];
// Uses the spread operator to spread out old values into the new array literalconst newArr1 = [...oldArr];
// Slice with no arguments returns the newly copied Arrayconst newArr2 = oldArr.slice();
// Map applies the callback to every element in the array and returns a new arrayconst newArr3 = oldArr.map((el) => el);
// Concat is used to merge arrays and returns a new array. Concat with no args copies an arrayconst newArr4 = oldArr.concat();
// Object.assign can be used to transfer all the properties into a new array literalconst newArr5 = Object.assign([], oldArr);
// Creating via the Array constructor using the new keywordconst newArr6 = new Array(...oldArr);
// For loopfunction clone(base) {const newArray = [];for(let i= 0; i < base.length; i++) {newArray[i] = base[i];}return newArray;}
const newArr7 = clone(oldArr);
console.log(newArr1, newArr2, newArr3, newArr4, newArr5, newArr6, newArr7);
嵌套数组或对象时要小心!:
当嵌套数组时,值将通过引用复制。这是一个如何导致问题的示例:
let arr1 = [1,2,[1,2,3]]
let arr2 = [...arr1];
arr2[2][0] = 5; // we change arr2
console.log(arr1); // arr1 is also changed because the array inside arr1 was copied by reference
let arr1 = [1,2,[1,2,3]]
let arr2 = JSON.parse(JSON.stringify(arr1)) ;
arr2[2][0] = 5;
console.log(arr1); // now I'm not modified because I'm a deep clone
var arr1 = ['a','b','c'];// arr1 and arr2 are independent and primitive elements are stored in// different places in the memoryvar arr2 = arr1.slice();arr2.push('d');console.log(arr1); // [ 'a', 'b', 'c' ]console.log(arr2); // [ 'a', 'b', 'c', 'd' ]
如果数组中的元素是对象文字,另一个数组 ({}, [])
var arr1 = [{ x: 'a', y: 'b'}, [1, 2], [3, 4]];// arr1 and arr2 are independent and reference's/addresses are stored in different// places in the memory. But those reference's/addresses points to some common place// in the memory.var arr2 = arr1.slice();arr2.pop(); // OK - don't affect arr1 bcos only the address in the arr2 is// deleted not the data pointed by that addressarr2[0].x = 'z'; // not OK - affect arr1 bcos changes made in the common area// pointed by the addresses in both arr1 and arr2arr2[1][0] = 9; // not OK - same above reason
console.log(arr1); // [ { x: 'z', y: 'b' }, [ 9, 2 ], [ 3, 4 ] ]console.log(arr2); // [ { x: 'z', y: 'b' }, [ 9, 2 ] ]
// If a is array:// then call cpArr(a) for each e;// else return a
const cpArr = a => Array.isArray(a) && a.map(e => cpArr(e)) || a;
let src = [[1,2,3], [4, ["five", "six", 7], true], 8, 9, false];let dst = cpArr(src);
const arr1 = [['item 1-1', 'item 1-2'], ['item 2-1', 'item 2-2'], ['item 3-1', 'item 3-2']];
/*** Using Spread operator, it will create a new array with no reference to the first level.** Since, the items are not primitive, they get their own references. It means that any change on them,* it will be still reflected on the original object (aka arr1).*/const arr2 = [...arr1];
/*** Using Array.prototype.map() in conjunction Array.prototype.slice() will ensure:* - The first level is not a reference to the original array.* - In the second level, the items are forced (via slice()) to be created as new ones, so there is not reference to the original items*/const arr3 = arr1.map(item => item.slice());