js对象的深拷贝方法

对象的深拷贝与浅拷贝的区别如下:
浅拷贝:仅仅复制对象的引用,而不是对象本身;
深拷贝:把复制的对象所引用的全部对象都复制一遍。


深拷贝的几种方法如下:

1. 利用 JSON.stringify() JSON.parse() 序列化和反序列

代码如下:

function deepCopy(obj){ 
    let data = JSON.stringify(obj)
    let newData = JSON.parse(data)
    return newData
}

先将需要拷贝的对象进行JSON字符串化,然后再pase解析出来,赋给另一个变量,实现深拷贝。
缺点:部分数据类型在JSON字符串化后会丢失;
这是因为JSON在执行字符串化的这个过程时,会先进行一个JSON格式化,获得安全的JSON值;
因此如果是非安全的JSON值,就会被丢弃掉。其中undefined、function、symbol这三种类型的值就是非安全的,所以格式化后,就被过滤掉了
set、map这种数据格式的对象,也并没有被正确处理,而是处理成了一个空对象。

2. Object.assign(target, source1, source2)

可以用于对象合并,将源对象的所有可枚举属性,复制到目标对象上。
代码如下:

var data = {
              a: "123",
              b: 123,
              c: true,
              d: [43, 2],
              e: undefined,
              f: null,
              g: function() {    console.log("g");  },
              h: new Set([3, 2, null]),
              i: Symbol("fsd"),
              k: new Map([    ["name", "张三"],    ["title", "Author"]  ])
        };

var newData = Object.assign({},data)
console.log(newData) 

newData 则为深拷贝后的对象;
这个方法也有一个缺点:
这种方式的拷贝,如果源目标对象中某个属性值是对另一个对象的引用,那么这个属性的拷贝仍然是对引用的拷贝。

var test = {  name: '张三' }
var data = { 
              a: 123,
              b: test
            }
var newData = Object.assign({},data)
console.log(newData) 
// {  a: 123,  b: {    name: '张三'  }}
test.age = 18
console.log(newData)
// {  a: 123,  b: {    name: '张三',   age: 18  }}

3. 迭代递归

参考别人的代码:

function deepCopy(data) {
      if(typ data !== 'object' || data === null){
            throw new TypeError('传入参数不是对象')
        }
      let newData = {};
      const dataKeys = Object.keys(data);
      dataKeys.forEach(value => {
         const currentDataValue = data[value];
         // 基本数据类型的值和函数直接赋值拷贝 
         if (typ currentDataValue !== "object" || currentDataValue === null) {
              newData[value] = currentDataValue;
          } else if (Array.isArray(currentDataValue)) {
             // 实现数组的深拷贝
            newData[value] = [...currentDataValue];
          } else if (currentDataValue instanc Set) {
             // 实现set数据的深拷贝
             newData[value] = new Set([...currentDataValue]);
          } else if (currentDataValue instanc Map) {
             // 实现map数据的深拷贝
             newData[value] = new Map([...currentDataValue]);
          } else { 
             // 普通对象则递归赋值
             newData[value] = deepCopy(currentDataValue);
          } 
       }); 
      return newData;
  }

引用文章:
https://www.javascriptcn.com/read-96160.html

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • 文编:王哟哟内容摘自于网络 公众号“字匠”推荐往期精选 山海经怪物列表(东方神界资料)关于风水的常用术语……报道和...
    王哟哟阅读 3,671评论 0 0
  • 英芷阅读 1,560评论 0 0
  • 姑娘留步,小生不才。 能否为我止步, 我愿用我半生艰苦, 换走您半夏阴影。 自此所有爱慕之意, 止于唇齿,溺于青春...
    静义阅读 1,495评论 0 1
  • “这个世界上人们为什么会画画、跳舞、音乐、建筑等艺术,因为可以通过这些东西表达自己的内心。没有一个人能像艺术一样认...
    约读阅美阅读 1,170评论 0 0