javascript中的深拷贝和浅拷贝

时间:2021-09-12 22:07:59

有时候我们需要拿到对象和数组进行操作却避免其受影响,就需要拷贝一份新的出来。

对于字符串的拷贝是对其值进行复制:

let person1="zs"; let person2=person1;//复制 person2="ls";//改变person2的值并不会影响到person1 console.log(person1);//zs console.log(person2);//ls

对对象的拷贝:

let person1={
  name:"zs",
  age:66,
  sex:"female",
  grandson:{
    name:"ls",
    age:18,
    sex:"male"
  }
}
//注:执行蓝色标题下代码时将别的蓝色标题下代码注释
//我理解的这种才是浅拷贝
let person2=person1;//复制的是引用地址,person2和person1指向同一个引用地址
person2.age=80;
person2.grandson.age=20;
console.log(person1.age);//80
console.log(person1.grandson.age);//20
//ES6中有新的方法对对象进行克隆
let person3=Object.assign({},person1);//有人理解这种也是浅拷贝
person3.age=50;
console.log(person1.age);
//66
console.log(person3.age);//50
//发现了没?person1的age并未收到影响,person3拷贝出来的指向新的引用地址?是的
person3.grandson.age=40;//改变了person3中子对象中的age
console.log(person1.grandson.age);//40,person1中grandson的age发生了变化,说明person3只拷贝了一级,看下图
javascript中的深拷贝和浅拷贝

 



 图中是我的理解,Object.assign()只实现了一级克隆,当然对于没有嵌套的对象可以直接用,可是对于多层嵌套的对象,也想对其子对象进行克隆这种方法就不行了。

通常对数组的拷贝:1. [].concact(arr),2.arr.slice(0).这两种方法和Object.assign()作用一样,对于一维数组就ok,二维数组或多维数组就没辙了。

深拷贝:完全复制一份新的对象出来,和原对象就没有任何瓜葛了,完全指向新的引用地址(包括子代对象)

最简单的一种: JSON.parse(JSON.stringify(obj)),但是这种方法对obj的要求必须是符合json格式,像正则等都不能用这种方法了。

第二种就是递归:

var copyObj = function(obj){
    var newobj = obj.constructor === Array ? [] : {};
    if(typeof obj !== 'object'){
        return;
    } else {
        for(var i in obj){
            newobj[i] = typeof obj[i] === 'object' ? 
            copyObj(obj[i]) : obj[i]; 
        }
    }
    return newobj;
}

  以上纯属个人理解,欢迎指正。