js浅拷贝与深拷贝的理解

拷贝

第一种情况 普通赋值

let a = 1
let b = a
b = 2
console.log(a) // 1
console.log(b) // 2

但如果a是一个对象objA

let objA = {
  name: 'ming',
  age: 18,
}
let objB = {}
objB = objA
objB.age = 20
console.log(objA.age) // 20
console.log(objB.age) // 20

原本只是想修改objB中的age属性值,但同时也修改了objA的age属性值。为了不影响objA,这个时候就需要拷贝了。

浅拷贝

let objA = {
  name: 'ming',
  age: 18,
}
let objB = {}
// -------------实现浅拷贝--------------
// 普通循环赋值
for (let i in objA) {
  objB[i] = objA[i]
}
// --------其他可以实现浅拷贝的方法--------
// Object.assign(objB, objA)  // Object.assign(target, ...sources)
// objB = { ...objA } // 解构赋值
// 如果引用类型是数组 还可以使用slice()方法

objB.age = 100
console.log(objA.age) // 18
console.log(objB.age) // 100

但如果objA中有一个引用类型属性。如下

let objA = {
  name: 'ming',
  age: 18,
  info: {
    sex: 'man'
  }
}
let objB = {}
// 浅拷贝
objB = { ...objA }
objB.info.sex = 'woman'
console.log(objA.info.sex) // woman
console.log(objB.info.sex) // woman

修改了objB.info的sex属性依旧会影响objB.info的sex属性。也就是浅拷贝只能拷贝一层,如果是引用类型的只能拷贝引用,所以这个时候需要深拷贝了

let objA = {
  name: 'ming',
  age: 18,
  info: {
    sex: 'man'
  }
}
let objB = {}
// 深拷贝
function deepClone(obj) {
  let objClone = Array.isArray(obj) ? [] : {};
  if (obj && typeof obj === "object") {
    for (key in obj) {
      if (obj.hasOwnProperty(key)) {
        //判断ojb子元素是否为对象,如果是,递归复制
        if (obj[key] && typeof obj[key] === "object") {
          objClone[key] = deepClone(obj[key]);
        } else {
          //如果不是,简单复制
          objClone[key] = obj[key];
        }
      }
    }
  }
  return objClone;
}

objB = deepClone(objA)

// objB = JSON.parse(JSON.stringify(objA)) // 或者使用这种方法深拷贝
objB.info.sex = 'woman'
console.log(objA.info.sex) // man
console.log(objB.info.sex) // woman

这个时候objA与objB互不影响

总结

基本类型:undefined,null,Boolean,Number和String
引用类型:对象、数组、函数等

浅拷贝就是将值简单的赋给其他变量,如果是引用类型的只能拷贝引用(引用指的是同一个地址) ,公用同一个地址。
在这里插入图片描述
深拷贝真正意义上的拷贝。遇到引用类型时,会在堆中开辟新的空间,复制的引用类型的引用指向这个新的地址。与原数据互不影响。
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值