将 JavaScript 中的数组复制到另一个数组时:
var arr1 = ['a','b','c'];
var arr2 = arr1;
arr2.push('d'); //Now, arr1 = ['a','b','c','d']
我意识到 arr2
指的是与 arr1
相同的数组,而不是一个新的独立数组。如何复制数组以获得两个独立的数组?
原文由 Dan 发布,翻译遵循 CC BY-SA 4.0 许可协议
在 Javascript 中,深度复制技术依赖于数组中的元素。让我们从那里开始。
元素可以是:文字值、文字结构或原型。
// Literal values (type1)
const booleanLiteral = true;
const numberLiteral = 1;
const stringLiteral = 'true';
// Literal structures (type2)
const arrayLiteral = [];
const objectLiteral = {};
// Prototypes (type3)
const booleanPrototype = new Bool(true);
const numberPrototype = new Number(1);
const stringPrototype = new String('true');
const arrayPrototype = new Array();
const objectPrototype = new Object(); // or `new function () {}
从这些元素我们可以创建三种类型的数组。
// 1) Array of literal-values (boolean, number, string)
const type1 = [ true, 1, "true" ];
// 2) Array of literal-structures (array, object)
const type2 = [ [], {} ];
// 3) Array of prototype-objects (function)
const type3 = [ function () {}, function () {} ];
根据数组中元素的类型,我们可以使用各种技术来进行深拷贝。
https://www.measurethat.net/Benchmarks/Show/17502/0/deep-copy-comparison
The [ ...myArray ]
, myArray.splice(0)
, myArray.slice()
, and myArray.concat()
techniques can be used to deep copy arrays with literal values (boolean, number, and仅字符串);其中 slice()
在Chrome中性能最高,spread ...
在Firefox中性能最高。
JSON.parse(JSON.stringify(myArray))
技术可用于深度复制文字值(布尔值、数字、字符串)和文字结构(数组、对象),但不能用于原型对象。
所有数组(type1、type2、type3)
function copy(aObject) {
// Prevent undefined objects
// if (!aObject) return aObject;
let bObject = Array.isArray(aObject) ? [] : {};
let value;
for (const key in aObject) {
// Prevent self-references to parent object
// if (Object.is(aObject[key], aObject)) continue;
value = aObject[key];
bObject[key] = (typeof value === "object") ? copy(value) : value;
}
return bObject;
}
var arr1 = ['a','b','c'];
var arr2 = arr1;
我意识到 arr2 指的是与 arr1 相同的数组,而不是一个新的独立数组。如何复制数组以获得两个独立的数组?
因为 arr1
是一个文字值数组(布尔值、数字或字符串),您可以使用上面讨论的任何深度复制技术,其中 slice()
和传播 ...
具有最高的性能。
arr2 = arr1.slice();
arr2 = [...arr1];
arr2 = arr1.splice(0);
arr2 = arr1.concat();
arr2 = JSON.parse(JSON.stringify(arr1));
arr2 = copy(arr1); // Custom function needed, and provided above
arr2 = _.cloneDeep(arr1); // Lo-dash.js needed
arr2 = jQuery.extend(true, [], arr1); // jQuery.js needed
原文由 tim-montague 发布,翻译遵循 CC BY-SA 4.0 许可协议
10 回答11.1k 阅读
6 回答3k 阅读
5 回答4.8k 阅读✓ 已解决
4 回答3.1k 阅读✓ 已解决
2 回答2.6k 阅读✓ 已解决
3 回答2.3k 阅读✓ 已解决
3 回答2.1k 阅读✓ 已解决
用这个:
基本上,
slice()
操作会克隆数组并返回对新数组的引用。另请注意:
对于引用、字符串和数字(而不是实际对象),
slice()
将对象引用复制到新数组中。 原始数组和新数组都引用同一个对象。如果引用的对象发生更改,则更改对新数组和原始数组都可见。字符串和数字等原语是不可变的,因此不可能更改字符串或数字。