我们提供安全,免费的手游软件下载!
深拷贝和浅拷贝是JavaScript中处理对象和数据复制操作的两种方式。在探讨深浅拷贝之前,我们需要先了解JavaScript中的两种数据类型:
基本数据类型包括String、Number、Object、Boolean、null、undefined和symbol(ES6+)。
而引用数据类型则包括Object(如function、Array和正则表达式等都是对象)。
在JavaScript中,基本数据类型存储在栈中,而引用类型存储在堆内存中的对象。基本数据类型按值存放,可以直接按值访问。引用类型存储在堆内存中,栈内存中保存对堆内存中对象的引用地址。
浅拷贝是创建一个新的数据,该数据包含原始数据属性的一份精确拷贝。如果属性是基本类型,拷贝的就是基本类型的值。如果属性是引用类型,拷贝的是内存地址,因此浅拷贝只拷贝一层,深层次的引用类型会共享内存地址。
以下用一张图解释了浅拷贝:
var obj = {
age: 18,
person: {
name1: 'fx',
name2: 'xka'
},
list:['hhh','666'],
love: function () {
console.log('嘿嘿')
}
}
var newObj = Object.assign({}, obj);
// 因为是浅拷贝,所以只拷贝了基本类型的,引用类型还是共享内存地址的,即改变obj的引用类型的内容,newObj里面的引用类型的值也随之改变
obj.person.name1='xxx'
obj.list[0]='xxx'
console.log(newObj.person.name1) //xxx
const fxArr = ["One", {
name: "Two",
age: 20
}, "Three"]
const fxArrs = fxArr.slice(0,)
fxArr[1].name = "four";
console.log(fxArrs[1].name) //four
const fxArr = ["One", {
name: "Two",
age: 20
}, "Three"]
const fxArrs = fxArr.concat()
fxArr[1].name = "four";
console.log(fxArrs[1].name) //four
const fxArr = ["One", {
name: "Two",
age: 20
}, "Three"]
const fxArrs = [...fxArr]
fxArr[1].name = "four";
console.log(fxArrs[1].name) //four
深拷贝会开辟一个新的栈空间,两个对象完全相同,但对应不同的地址。修改一个对象的属性不会改变另一个对象的属性。
以下用一张图解释了深拷贝:
var obj = {
age: 18,
person: {
name1: 'fx',
name2: 'xka'
},
list:['hhh','666'],
love: function () {
console.log('嘿嘿')
}
}
const obj2=JSON.parse(JSON.stringify(obj));
obj.person.name1='6666'
console.log(obj2.person.name1) //fx
JSON.parse是经常使用的方法。然而,之前听说过的lodash的cloneDeep和jq的extend我都没有使用过。JSON.parse的一个缺点是它会忽略包含undefined、function和symbol的数据。这也是一个优点,因为可以利用其特性排除undefined等数据,获取干净的数据。另一个缺点是在处理大型数据时可能存在性能问题。
function clone(object){
const newObj={}
for(let proto in object){
if(object.hasOwnProperty(proto)){
newObj[proto]= object[proto]
}
}
return newObj
}
var obj = {
age: 18,
person: {
name1: 'fx',
name2: 'xka'
},
list:['hhh','666'],
love: function () {
console.log('嘿嘿')
}
}
const obj1=clone(obj)
console.log(obj)
console.log(obj1)
// 手写深拷贝
function deepClone(obj, hash = new WeakMap()) {
// 数据过滤
if (obj === null) return obj;
if (obj instanceof Date) return new Date(obj);
if (obj instanceof RegExp) return new RegExp(obj);
if (typeof obj !== "object") return obj;
if (hash.get(obj)) return hash.get(obj);
let cloneObj = new obj.constructor();
hash.set(obj, cloneObj);
for (let key in obj) {
if (obj.hasOwnProperty(key)) {
cloneObj[key] = deepClone(obj[key], hash);
}
}
return cloneObj;
}
var obj = {
age: 18,
person: {
name1: 'fx',
name2: 'xka'
},
list:['hhh','666'],
love: function () {
console.log('嘿嘿')
}
}
const obj2 = deepClone(obj) // 深拷贝
const obj3 = Object.assign({}, obj) // 浅拷贝
const obj4 = clone(obj) // 浅拷贝
obj.person.name1 = 'hhh';
console.log(obj2.person.name1) //fx
console.log(obj3.person.name1) //hhh
console.log(obj4.person.name1) //hhh
以上内容为个人学习整理,水平有限,如有错误之处,敬请指正。若觉得不错,请点击推荐和关注!谢谢~๑•́₃•̀๑ [鲜花][鲜花][鲜花]
热门资讯