深拷貝和淺拷貝最根本的區別在因而否是真正獲取了一個對象的複製實體,而不是引用,javascript
深拷貝的實現:
1.經過遞歸解決java
var a={a:23,b:[1,2,3,[5]],c:{name:'南京'}}; function deepCopy(initObj,finalObj) { var obj=finalObj||{}; for(var i in initObj){ var prop = initObj[i]; // 避免相互引用對象致使死循環,如initalObj.a = initalObj的狀況 if(prop === obj) { continue; } if(typeof initObj[i]==='object'){ obj[i]=(initObj[i].constructor===Array)?[]:{}; // arguments.callee(initObj[i],obj[i]); deepCopy(initObj[i],obj[i]); }else{ obj[i]=initObj[i]; } } return obj; } var b=deepCopy(a); b['name']='武漢'; b.c.name='長江'; console.log(a); console.log(b);
2.使用Object.create數組
var a={a:23,b:[1,2,3,[5]],c:{name:'南京'}}; function deepCopy(initObj,finalObj) { var obj=finalObj||{}; for(var i in initObj){ var prop=initObj[i]; if(prop===obj){ continue; } if(typeof prop==='object'){ // obj[i]=prop.constructor==='Array'?[]:Object.create(prop); // obj[i]=prop.isPrototypeOf(Array)?[]:Object.create(prop); obj[i]=prop instanceof Array?[]:Object.create(prop); }else{ obj[i]=prop; } } return obj; } var b=deepCopy(a); b['name']='武漢'; b.c.name='長江'; console.log(a); console.log(b);
3.藉助JSON函數
var a={a:23,b:[1,2,3,[5]],c:{name:'南京'},d:function () { console.log("hh"); }}; var b=JSON.parse(JSON.stringify(a)); b['name']='武漢'; b.c.name='長江'; console.log(a); console.log(b); console.log(a.d); console.log(b.d);
這種方法的缺點是沒法複製函數,再就是原型鏈沒了,對象就是object,所屬的類沒了.
四、Object.assign()處理一層的深度拷貝code
var a={name:'武漢',num:[1,2,3]}; var b=Object.assign({},a); b.name='南京'; console.log(a); console.log(b);
數組的拷貝,ES6有Array.from和...兩種方法不會發生引用,js中的slice和concat對象
var a=[1,2]; var b=Array.from(a); b.push(3); var c=[...a]; c.push(4); var d=a.slice(0); d.push(-1); var e=a.concat([5]); console.log(a); //[1,2] console.log(b); //[1,2,3] console.log(c); //[1,2,4] console.log(d); //[1,2,-1] console.log(e); //[1,2,5]