JS基础:14、深拷贝、浅拷贝

879 阅读1分钟

引言

不管是浅拷贝还是深拷贝都是针对引用类型的复制

浅拷贝

浅拷贝指的是只拷贝堆地址的引用

var arr = [1,2,3];
var arrs = arr; // 复制
arrs.push(4); // 修改复制
console.log(arr); // [1, 2, 3, 4] arr也发生改变

深拷贝

堆内存中开辟一块新的空间,把原对象的值复制到新的空间,引用指向新的地址

var arr = [1,2,3];
var arrs = JSON.parse(JSON.stringify(arr)); // 复制
arrs.push(4); // 修改复制
console.log(arr); // [1, 2, 3] arr不发生改变
console.log(arrs); // [1, 2, 3, 4]

对象深拷贝方法

1、JSON方法

缺点是:属性undefined无法复制,属性function无法复制

function deepClone(obj) {
    return JSON.parse(JSON.stringigy(obj));
}

2、递归 同样适用于数组深拷贝

function deepClone(obj){
  let objClone =  Array.isArray(obj) ? [] : {}; // 先判断是不是数组
  if (obj && typeof obj === 'object') { // 确定是引用类型
    for(let key in obj){
      if (obj[key] && typeof obj[key] === 'object'){ // 判断是否有深层嵌套
        objClone[key] = deepClone(obj[key]);
      }else{
        objClone[key] = obj[key]
      }
    }
  }
  return objClone;
}

3、Object.assign(target, …sources)

缺点:只能深拷贝一级属性,二级以上属性就是浅拷贝

function deepClone(obj,sources) {
    return Object.assign(obj, ...sources) // obj: 目标对象 sources:源对象
}

4、jquery的extend

// deep 深拷贝 , target 数据源, object 要合并的对象
$.extend( [deep ], target, object1 [, objectN ] )

数组深拷贝

1、for

// 基本数据类型
function deepCloneArr(arr) {
    let res = [];
    for(let i = 0; i < arr.length; i ++){
        res.push(arr[i])
    }
    return res;
}

2、concat()

// 基本数据类型
function deepCloneArr(arr) {
    return [].concat(arr);
}

3、slice()

// 基本数据类型
function deepCloneArr(arr) {
    return arr.slice();
}

4、JSON

// 复杂数据类型
function deepCloneArr(arr) {
    return JSON.parse(JSON.stringify(arr));
}

5、扩展运算符 ...

// 基本数据类型
function deepCloneArr(arr) {
    return [...arr];
}