JavaScript 浅拷贝与深拷贝
深浅拷贝区别
深拷贝和浅拷贝只针对像 Object, Array 这样的复杂对象(引用类型)的。
复制引用(引用类型)的拷贝方法称之为浅拷贝,也因为直接复制引用类型,导致新旧对象共用一块内存地址,会互相影响,具体看例子
深拷贝就是指完全的拷贝一个对象,将原对象的各个属性递归复制下来。这样即使嵌套了对象,两者也相互分离。
浅拷贝
var shallowCopy = function(obj) { if (typeof obj !== 'object') return; // 只拷贝对象 var newObj = obj instanceof Array ? [] : {}; // 根据obj的类型判断是新建一个数组还是对象 for (var key in obj) { // 遍历obj,并且判断是obj的属性才拷贝 if (obj.hasOwnProperty(key)) { newObj[key] = obj[key]; } } return newObj; } var obj = { a:1, arr: [2,3] }; var shallowObj = shallowCopy(obj); shallowObj.arr[1] = 5; console.log(obj.arr[1]) // 5 shallowObj.a = 5; console.log(obj.a) // 1
备注:
①hasOwnProperty() 方法会返回一个布尔值,指示对象自身属性中是否具有指定的属性。Object.prototype.hasOwnProperty();
②instanceof 运算符用来测试一个对象在其原型链中是否存在一个构造函数的 prototype 属性。
原理
遍历对象,然后把属性和属性值都放在一个新的对象
具体:判断是参数否为对象,是数组还是object;用 for in 遍历所传的参数对象,并用 if (arg.hasOwnProperty(prop)) 忽略掉继承属性,然后赋值给临时创建的对象,最后返回此对象。
深拷贝
实现一个深拷贝在拷贝的时候判断一下属性值的类型,如果是对象,我们递归调用深拷贝函数就OK了
var deepCopy = function(obj) { if (typeof obj !== 'object') return; var newObj = obj instanceof Array ? [] : {}; for (var key in obj) { if (obj.hasOwnProperty(key)) { newObj[key] = typeof obj[key] === 'object' ? deepCopy(obj[key]) : obj[key]; } } return newObj; } var obj = { a:1, arr: [2,3] }; var shallowObj = shallowCopy(obj); shallowObj.arr[1] = 5; console.log(obj.arr[1]) // 3 shallowObj.a = 5; console.log(obj.a) // 1
性能问题
尽管使用深拷贝会完全的克隆一个新对象,不会产生副作用,但是深拷贝因为使用递归,性能会不如浅拷贝,在开发中,还是要根据实际情况进行选择。
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论