可能重复:
What is the most efficient way to clone a JavaScript object?
我需要复制一个(有序的,非关联的)对象数组。我正在使用jQuery。我最初尝试过
jquery.extend({}, myArray)
但是,当然,这给了我一个对象,我需要一个数组(顺便说一下,真的很喜欢jquery.extend)。
那么,复制数组的最佳方法是什么?
答案 0 :(得分:277)
由于Array.slice()不进行深度复制,因此不适合多维数组:
var a =[[1], [2], [3]];
var b = a.slice();
b.shift().shift();
// a is now [[], [2], [3]]
请注意,虽然我上面使用了shift().shift()
,但重点是 b[0][0]
包含指向a[0][0]
的指针,而不是值。
同样delete(b[0][0])
也会导致a[0][0]
被删除,b[0][0]=99
也会将a[0][0]
的值更改为99.
当一个真值作为初始参数传递时,jQuery的extend
方法 执行深层复制:
var a =[[1], [2], [3]];
var b = $.extend(true, [], a);
b.shift().shift();
// a is still [[1], [2], [3]]
答案 1 :(得分:28)
$.extend(true, [], [['a', ['c']], 'b'])
那应该为你做。
答案 2 :(得分:19)
我意识到你正在寻找一个数组的“深层”副本,但是如果你只有一个单级数组就可以使用它:
复制本机JS数组非常简单。使用Array.slice()方法创建数组的部分/全部副本。
var foo = ['a','b','c','d','e'];
var bar = foo.slice();
现在foo和bar是'a','b','c','d','e'的5个成员数组
当然吧是一个副本,而不是一个参考...所以如果你下次这样做...
bar.push('f');
alert('foo:' + foo.join(', '));
alert('bar:' + bar.join(', '));
你现在得到:
foo:a, b, c, d, e
bar:a, b, c, d, e, f
答案 3 :(得分:13)
JavaScript中的所有东西都是通过引用传递的,所以如果你想要一个真正的数组对象的深层副本,我能想到的最好的方法是将整个数组序列化为JSON,然后反序列化它。 / p>
答案 4 :(得分:7)
如果您想使用纯JavaScript,请尝试以下方法:
var arr=["apple","ball","cat","dog"];
var narr=[];
for(var i=0;i<arr.length;i++){
narr.push(arr[i]);
}
alert(narr); //output: apple,ball,vat,dog
narr.push("elephant");
alert(arr); // output: apple,ball,vat,dog
alert(narr); // apple,ball,vat,dog,elephant
答案 5 :(得分:2)
我遇到了这个“深层对象复制”功能,我发现它可以方便地按值复制对象。它不使用jQuery,但肯定很深。
http://www.overset.com/2007/07/11/javascript-recursive-object-copy-deep-object-copy-pass-by-value/
答案 6 :(得分:2)
我打算在jPaq的下一个版本中发布此代码,但在此之前,如果您的目标是对数组执行深层复制,则可以使用此代码:
Array.prototype.clone = function(doDeepCopy) {
if(doDeepCopy) {
var encountered = [{
a : this,
b : []
}];
var item,
levels = [{a:this, b:encountered[0].b, i:0}],
level = 0,
i = 0,
len = this.length;
while(i < len) {
item = levels[level].a[i];
if(Object.prototype.toString.call(item) === "[object Array]") {
for(var j = encountered.length - 1; j >= 0; j--) {
if(encountered[j].a === item) {
levels[level].b.push(encountered[j].b);
break;
}
}
if(j < 0) {
encountered.push(j = {
a : item,
b : []
});
levels[level].b.push(j.b);
levels[level].i = i + 1;
levels[++level] = {a:item, b:j.b, i:0};
i = -1;
len = item.length;
}
}
else {
levels[level].b.push(item);
}
if(++i == len && level > 0) {
levels.pop();
i = levels[--level].i;
len = levels[level].a.length;
}
}
return encountered[0].b;
}
else {
return this.slice(0);
}
};
以下是如何调用此函数来执行递归数组的深层复制的示例:
// Create a recursive array to prove that the cloning function can handle it.
var arrOriginal = [1,2,3];
arrOriginal.push(arrOriginal);
// Make a shallow copy of the recursive array.
var arrShallowCopy = arrOriginal.clone();
// Prove that the shallow copy isn't the same as a deep copy by showing that
// arrShallowCopy contains arrOriginal.
alert("It is " + (arrShallowCopy[3] === arrOriginal)
+ " that arrShallowCopy contains arrOriginal.");
// Make a deep copy of the recursive array.
var arrDeepCopy = arrOriginal.clone(true);
// Prove that the deep copy really works by showing that the original array is
// not the fourth item in arrDeepCopy but that this new array is.
alert("It is "
+ (arrDeepCopy[3] !== arrOriginal && arrDeepCopy === arrDeepCopy[3])
+ " that arrDeepCopy contains itself and not arrOriginal.");
您可以使用此代码here at JS Bin。