JS對象的引用,對象的拷貝
阿新 • • 發佈:2018-04-26
遞歸 func cnblogs div 無法拷貝 script keyword js對象 var
[Toc]
一、場景
除了基本類型跟null,對象之間的賦值,只是將地址指向同一個,而不是真正意義上的拷貝
將一個對象賦值給另外一個對象。
var a = [1,2,3];
var b = a;
b.push(4); // b中添加了一個4
alert(a); // a變成了[1,2,3,4]
自定義對象
var obj = {a:10};
var obj2 = obj;
obj2.a = 20; // obj2.a改變了,
alert(obj.a); // 20,obj的a跟著改變
這就是由於對象類型直接賦值,只是將引用指向同一個地址,導致修改了obj會導致obj2也被修改
二、淺拷貝
所以,我們需要封裝一個函數,來對對象進行拷貝,通過for in 循環獲取基本類型,賦值每一個基本類型,才能真正意義上的復制一個對象
var obj = {a:10};
function copy(obj){
var newobj = {};
for ( var attr in obj) {
newobj[attr] = obj[attr];
}
return newobj;
}
var obj2 = copy(obj);
obj2.a = 20;
alert(obj.a); //10
這樣就解決了對象賦值的問題。
三、深拷貝
但是這裏存在隱患,如果obj中,a的值不是10,而是一個對象,這樣就會導致在for in中,將a這個對象的引用賦值為新對象,導致存在對象引用的問題。
var obj = {a:{b:10}};
function copy(obj){
var newobj = {};
for ( var attr in obj) {
newobj[attr] = obj[attr];
}
return newobj;
}
var obj2 = copy(obj);
obj2.a.b = 20;
alert(obj.a.b); //20
因此,由於這個copy對象只是對第一層進行拷貝,無法拷貝深層的對象,這個copy為淺拷貝,我們需要通過遞歸,來拷貝深層的對象。將copy改造成遞歸即可
var obj = {a:{b:10}};
function deepCopy(obj){
if(typeof obj != ‘object‘){
return obj;
}
var newobj = {};
for ( var attr in obj) {
newobj[attr] = deepCopy(obj[attr]);
}
return newobj;
}
var obj2 = deepCopy(obj);
obj2.a.b = 20;
alert(obj.a.b); //10
JS對象的引用,對象的拷貝