JavaScript:浅拷贝和深拷贝
来源:互联网 发布:seo推荐 编辑:程序博客网 时间:2024/06/05 04:29
阅读本文前,建议先弄明白JS变量中基本类型和引用类型的区别,这里可以参考我的另一篇博客:JavaScript变量和内存(参数按值传递解惑)。
浅拷贝
对于对象的遍历,我们用for…in语句,将一个对象的所有属性方法都拷贝赋值到另一个对象。如果,被拷贝的对象所有的属性都不是引用类型,那么也不会出现什么问题,可是如果被拷贝的对象某些属性是引用类型的,比如是个Object类型或者Array类型的,就会出问题,因为你赋值过去的只是该引用类型属性的的地址,并不是真的开辟空间进行了深度拷贝,所以,这些引用类型的属性是共享的,改变一个,另一个也改变了。
下面的例子,被拷贝的obj都不是引用类型,那么也就没什么问题。
但是,下面的例子,有的属性比如family和school是引用类型的属性,那么就出现了共享的问题:
深拷贝
深拷贝就是解决浅拷贝共享的问题,如果我们需要独立的拷贝出来的对象,互不影响的,那么我们需要使用深度拷贝来解决这个问题。
考虑到数组和对象的情况,我们需要在遍历的时候对属性的类型进行判断,如果是引用类型,我们就得注意了。
补充:关于callee的用法:
- callee返回正在执行的函数本身的引用,它是arguments的一个属性;
- 这个属性只有在函数执行的时候才有效;
- callee有个属性叫length,可以获得形参的个数,因此可以用来比较形参和实参个数是否一致,即比较arguments.length 是否等于 arguments.callee.length;
- 它可以用来递归匿名函数。
function test() { alert(arguments.callee);}
这个用途是递归:
其中函数内部包含了对sum自身的引用,函数名仅仅是个变量名,在函数内部调用sum即相当于调用一个全局变量,不能很好的体现出是调用自身,这时使用callee会是个比较好的方法。
考虑到数组和对象的情况,我们需要对传入的数据类型进行判断,通过如下的方法:
这里用到了arguments.callee()方法,它表示的是在哪个函数中执行,就代表哪个函数。在如下的代码中实际指向的是deepClone函数,也就是另一种递归调用的方式。
<!DOCTYPE html><html><head> <meta charset="utf-8"> <title>LazyLoad</title> <style type="text/css"> </style></head><body> <script type="text/javascript"> var obj = { name: 'guoyu', age: 28, sex: 'male', family: ['father','mather','sister'], school: { primary: 'ZGXX', middle: 'XYYZ', high: 'HZKJDX' }, fun: function() {alert('hello');} }; function isClass(o) { if (o == null) {return 'Null';} if (o == undefined) {return 'Undefined';} //toString返回的:'[object Array]',slice(8,-1)就是Array,返回类型 return Object.prototype.toString.call(o).slice(8, -1); } function deepClone(obj) { var result; var oClass = isClass(obj); if (oClass === 'Object') { result = {}; } else if (oClass === 'Array') { result = []; } else { return obj; } for (key in obj) { var copy = obj[key]; if (isClass(copy) === 'Object') { //递归调用 result[key] = arguments.callee(copy); alert(arguments.callee);//指的是deepClone这个函数本身 } else if (isClass(copy) === 'Array') { result[key] = arguments.callee(copy); } else { result[key] = obj[key]; } } return result; } var ret = deepClone(obj); </script></body></html>
阅读全文
1 0
- javascript中的深拷贝和浅拷贝
- javascript 深拷贝和浅拷贝
- JavaScript深拷贝和浅拷贝
- JavaScript深拷贝和浅拷贝
- javascript中的浅拷贝和深拷贝
- JavaScript的深拷贝和浅拷贝
- javascript中的深拷贝和浅拷贝?
- JavaScript 的深拷贝和浅拷贝
- javaScript中的浅拷贝和深拷贝
- JavaScript深拷贝和浅拷贝数组
- JavaScript:浅拷贝和深拷贝
- JavaScript 的深拷贝和浅拷贝
- javascript深拷贝和浅拷贝
- javascript深拷贝和浅拷贝
- JavaScript中的深拷贝和浅拷贝
- javascript中的深拷贝和浅拷贝?
- JavaScript之浅拷贝和深拷贝
- javascript中的深拷贝和浅拷贝
- sed基本用法
- IntelliJ IDEA 使用maven 集成SpringMVC+Hibernate
- 423. Reconstruct Original Digits from English
- 廖雪峰的Python-匿名函数-lambda
- 交叉熵代价函数(作用及公式推导)--转自CSDN
- JavaScript:浅拷贝和深拷贝
- SVN分支/合并原理及最佳实践2
- 结构体中使用string
- 5.4 线性相位FIR的优化设计
- 猿辅导分布式机器学习库ytk-learn、分布式通信库ytk-mp4j
- Flask Web开发 第一部分 第3章 模版
- mysql5.7 使用gtid复制时的参数设置
- Android点击WebView中的图片查看大图
- Java 线程池