JavaScript:利用递归实现对象深拷贝

先来普及一下深拷贝和浅拷贝的区别jquery

浅拷贝:就是简单的复制,用等号便可完成es6

let a = { a: 1 }
let b = a
复制代码

这就完成了一个浅拷贝 可是当修改对象b的时候,咱们发现对象a的值也被改变了npm

b.a = 10
console.log(a.a) => 10
复制代码

这是由于浅拷贝只复制了指向对象的指针,新旧对象共用同一块内存,修改某一个对象的同时也会把另外一个都一并修改了bash

深拷贝:跟浅拷贝最简单明了的区别就是修改拷贝的对象,不会改变源对象 利用Object.assign能够对只有一层的对象实现深拷贝,以下:函数

let a = { a: 1, b: 2, c: 3 }
let b = Object.assign({}, a)
b.b = 100
console.log(a.b) => 2
复制代码

能够看出来这样是彻底能够作到对只有一层的对象实现深拷贝的 可是若是对象里面的元素仍是对象的话就没做用了测试

let a = { a: 1, b: 2, c: 3, d: { a: 1 } }
let b = Object.assign({}, a)
b.d.a = 100
console.log(a.d.a) => 100
复制代码

对于这种比较复杂的对象,咱们就能够利用递归的方式实现真正的对象深拷贝了ui

function deepClone (sourceObj, targetObj) {
    let cloneObj = targetObj || {}
    if (!sourceObj || typeof sourceObj !== "object" || sourceObj.length === undefined) {
        return sourceObj
    }
    if (sourceObj instanceof Array) {
        cloneObj = sourceObj.concat()
    } else {
        for (let i in sourceObj) {
            if (typeof sourceObj[i] === 'object') {
                cloneObj[i] = deepClone(sourceObj[i], {})
            } else {
                cloneObj[i] = sourceObj[i]
            }
        }
    }
    return cloneObj
}
复制代码

简单的几行代码就能够轻松实现对象的深拷贝es5

简单的测试代码,以下:
let sourceObj = {
  a: 1,
  b: {
    a: 1
  },
  c: {
    a: 1,
    b: {
      a: 1
    }
  },
  d: function() {
    console.log('hello world')
  },
  e: [1, 2, 3]
}
let targetObj = deepClone(sourceObj, {})
targetObj.c.b.a = 9
console.log(sourceObj) => { a: 1,  b: { a: 1 },  c: { a: 1, b: { a: 1 } },  d: [Function: d],  e: [ 1, 2, 3 ] }
console.log(targetObj) => { a: 1,  b: { a: 1 },  c: { a: 1, b: { a: 9 } },  d: [Function: d],  e: [ 1, 2, 3 ] }
复制代码

另外介绍两个用来作深拷贝的库spa

**jquery**
使用方法:
let targetObj = $.extent(true,{},sourceObj)
**lodash函数库**
使用方法:
npm install lodash
**es5写法**
let lodash = require('lodash')
**es6写法**
import lodash from 'lodash'

let targetOj = lodash.cloneDeep(sourceObj)
复制代码

各位看官以为有什么地方不对的请多多指教。指针

相关文章
相关标签/搜索