1. 基本概念
● 深拷贝和浅拷贝针对的是引用类型。基本类型的名值存储在栈中,当复制时,栈内存会开辟一个栈内存。所以二者修改时,彼此不会影响。
● 浅拷贝复制的是指向对象的指针,并没有开辟新的栈内存,原对象和新对象还是共享同一块内存,修改新对象自然会影响原对象。
深拷贝会开辟新的栈内存,原对象和新对象不共享同一块内存,修改新对象不会影响到原对象。
2. 实现方式
不论是浅拷贝还是深拷贝,属性值是基本类型,修改其中一个对象,不会影响另一个对象的该属性。
浅拷贝:属性值是引用类型,由于拷贝的是对象的引用,共享相同的地址。
深拷贝:属性值是引用类型,开辟新的内存,互不影响。
2.1 浅拷贝的实现方式
● Object.assign()
● Array.prototype.concat()
● Array.prototype.slice()
● 引用复制
2.2 深拷贝的实现方式
● JSON.parse(JSON.stringify())
原理:
1. 用JSON.stringify将对象转成JSON字符串,再用JSON.parse()把字符串解析成对象。一去一来,新的对象产生了,而且对象会开辟新的栈,实现深拷贝。
2. 这种方法虽然可以实现数组或对象的深拷贝,但不能处理函数。因为JSON.stringify() 方法是将一个JavaScript值(对象或者数组)转换为一个 JSON字符串,不能接受函数
● 递归方法
原理:遍历对象、数组,直到里边都是基本数据类型,然后再去复制,即可实现深度拷贝。
该方法的局限性:
若属性值是函数、undefined、symbol时,会忽略掉。
● jQuery的$.extend()
jQuery.extend([deep], target, object1, [objectN]);
3. 赋值
赋值是把一个对象赋值给另一个变量时,并没有创建一个新对象,而是把原对象在栈中的地址(而非栈中的数据)赋给了新对象,即赋的是原对象在栈中的地址,原对象和新对象指向的是同一个地址。因此,两个对象的联动的,修改其中一个,另一个也会改变。包括里面所有的属性,不论是基本类型的数据,还是对象引用。
注意:赋值和拷贝是不同的概念,赋值的基本类型也会新开辟内存空间。基本数据类型栈中的指针也是值。
数据类型、变量、内存 参考链接:juejin.cn/post/701505…