文档章节

javaScript中的对象深度克隆

呵呵闯
 呵呵闯
发布于 2016/06/11 19:09
字数 601
阅读 6
收藏 0

克隆分为两种,一种是浅度克隆,另一种为深度克隆。

以下定义看看就行

浅度克隆:原始类型为值传递,对象类型仍为引用传递。

深度克隆:所有元素或属性均完全复制,与原对象完全脱离,也就是说所有对于新对象的修改都不会反映到原对象中。

以下为干货:

对于原始类型,克隆表现为简单地值传递。对于对象类型,原理就是通过for..in..遍历原对象,将原对象中的属性赋值到新的对象中。但是由于原对象中的属性不仅只有一层,可能属性中仍包含着新的对象,如果只遍历一次,那么获得的新对象的属性与原对象的深层对象之间自然是仍保持着引用关系,导致新对象与原对象没有实现完全脱离。所以就出现了浅度克隆和深度克隆的区分。

在网上看到了三种方法来实现深度克隆,但其实原理都是使用递归进行深度复制,只是使用的判断数据类型的方法不同。

代码中要注意,判断对象类型时不能使用typeof,因为Array类型和Object类型都会返回Object,但是Array类型和Object类型又是不同的。

以下代码对于所有类型的克隆均可实现

第一种方法:

//返回传递给他的任意对象的类
function isClass(o){
    if(o===null) return "Null";
    if(o===undefined) return "Undefined";
    return Object.prototype.toString.call(o).slice(8,-1);
}
//深度克隆
function deepClone(obj){
    var result,oClass=isClass(obj);
        //确定result的类型
    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);//递归调用
        }else if(isClass(copy)=="Array"){
            result[key]=arguments.callee(copy);
        }else{
            result[key]=obj[key];
        }
    }
    return result;
}

第二种方法:

function clone(obj) {
   var o;
   if (typeof obj == "object") {
       if (obj === null) {
           o = null;
       } else {
           if (obj instanceof Array) {
               o = [];
               for (var i = 0, len = obj.length; i < len; i++) {
                   o.push(clone(obj[i]));
               }
           } else {
               o = {};
               for (var j in obj) {
                   o[j] = clone(obj[j]);
               }
           }
       }
   } else {
       o = obj;
   }
   return o;
}

第三种方法:仅限于深度克隆对象

Object.prototype.Clone = function(){
  var objClone;
  if (this.constructor == Object){
    objClone = new this.constructor();
  }else{
    objClone = new this.constructor(this.valueOf());
  }
  for(var key in this){
    if ( objClone[key] != this[key] ){
    if ( typeof(this[key]) == 'object' ){
      objClone[key] = this[key].Clone();
    }else{
      objClone[key] = this[key];
    }
  }
}
  objClone.toString = this.toString;
  objClone.valueOf = this.valueOf;
  return objClone;
}

 

© 著作权归作者所有

共有 人打赏支持
呵呵闯
粉丝 3
博文 77
码字总数 20722
作品 0
深圳
程序员
私信 提问
js笔记十七之DOM操作-增删改

DOM的赠删改 增 真是项目中, 我们会在js中动态创建一些html标签, 然后把其增加到页面中 document.createElement 在js中动态创建一个html标签 appendChild 容器.appendChild(新元素) 把当前创...

uplyw
05/11
0
0
Object.assign()

https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/Object/assign 说明 Object.assign()方法将所有可枚举属性的值从一个或多个源对象复制到目标对象,然后返...

莫问今朝乄
2017/12/03
0
0
JS中的prototype的一些理解

JS中的phototype是JS中比较难理解的一个部分 本文基于下面几个知识点: 1 原型法设计模式 在.Net中可以使用clone()来实现原型法 原型法的主要思想是,现在有1个类A,我想要创建一个类B,这个类是...

Doublec
2015/05/14
0
0
前端开发:面向对象与javascript中的面向对象实现(二)构造函数与原型

前端开发:面向对象与javascript中的面向对象实现(二)构造函数与原型 前言(题外话):   有人说拖延症是一个绝症,哎呀治不好了。先不说这是一个每个人都多多少少会有的,也不管它究竟对...

grootzhang
2016/09/24
0
0
【zepto学习笔记02】零碎点

前言 上次我们看了zepto的选择器方面的东西,其实zepto简单很大程度是因为他用了最新的检索器querySelectorAll, 今天我们来学习下zepto的一些零碎点的地方吧,主要根据zepto官方文档顺序来 ...

panpanhtai
2014/07/09
0
0

没有更多内容

加载失败,请刷新页面

加载更多

开源 java CMS - FreeCMS2.8会员我的评论

项目地址:http://www.freeteam.cn/ 我的评论 从左侧管理菜单点击我的评论进入。在这里可以查看当前登录会员的所有评论记录。 删除评论 选择评论然后点击删除按钮可以完成删除操作。 为了防止...

freeteam
27分钟前
1
0
Eureka Server启用 https服务指北

文章共 591字,阅读大约需要 2分钟 ! 概 述 在我的前文《Eureka Server 开启Spring Security Basic认证》中已经给 Eureka Server 开启了最基本的鉴权措施,本文则让 HTTPS加持于 Eureka Ser...

CodeSheep
今天
17
0
OSChina 周二乱弹 —— 其实我在地板也睡不着

Osc乱弹歌单(2018)请戳(这里) 【今日歌曲】 @witt-z :分享歌词: 阴天 在不开灯的房间,当所有思绪都一点一点沉淀。 分享莫文蔚的单曲《阴天》: 《阴天》- 莫文蔚 手机党少年们想听歌,...

小小编辑
今天
714
12
微服务分布式事务实现

https://www.processon.com/view/link/5b2144d7e4b001a14d3d2d30

WALK_MAN
今天
5
0
《大漠烟尘》读书笔记及读后感文章3700字

《大漠烟尘》读书笔记及读后感文章3700字: 在这个浮躁的社会里,你有多久没有好好读完一本书了? 我们总觉得自己和别人不一样,所以当看到别人身上的问题时,很少有“反求诸己”,反思自己。...

原创小博客
今天
5
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部