0
点赞
收藏
分享

微信扫一扫

前端深拷贝和浅拷贝的深刻理解和使用场景

ixiaoyang8 2022-03-13 阅读 29

如何区分深拷贝与浅拷贝,简单点来说,就是假设B复制了A,当修改A时,看B是否会发生变化,如果B也跟着变了,说明这是浅拷贝,拿人手短,如果B没变,那就是深拷贝,自食其力。

A变B不变:深拷贝 A变B变:浅拷贝

拷贝涉及的概念是js的数据类型:栈堆,基本数据类型与引用数据类型

基本数据类型有哪些,number,string,boolean,null,undefined五类。

引用数据类型(Object类)有常规名值对的无序对象{a:1},数组[1,2,3],以及函数等。

深拷贝本身只针对较为复杂的object类型数据,因为基本数据类型的拷贝都不会各自影响,因为拷贝的时候是开辟了一个新的栈来存储。

深拷贝的实现:

1.递归方式,了解一下原理即可

Object 对象具有下列属性:

constructor

对创建对象的函数的引用(指针)。对于 Object 对象,该指针指向原始的 Object() 函数。

Prototype

对该对象的对象原型的引用。对于所有的对象,它默认返回 Object 对象的一个实例。

hasOwnProperty(property)

判断对象是否有某个特定的属性。必须用字符串指定该属性。(例o.hasOwnProperty("name"))

function deepClone(obj){
//Array.isArray判断是否是数组,不是则为对象
    let objClone = Array.isArray(obj)?[]:{};
    if(obj && typeof obj==="object"){
            //判断会否为引用数据类型,如果不是则直接拷贝即可
        for(key in obj){
               //for in 方法是用来遍历对象中的键的
            if(obj.hasOwnProperty(key)){
                //判断ojb子元素是否为对象,如果是,递归复制
                if(obj[key]&&typeof obj[key] ==="object"){
                    objClone[key] = deepClone(obj[key]);
                }else{
                    //如果不是,简单复制
                    objClone[key] = obj[key];
                }
            }
        }
    }
    return objClone;
}    
let a=[1,2,3,4],
    b=deepClone(a);
a[0]=2;
console.log(a,b);

2.除了递归,我们还可以借用JSON对象的parse和stringify

JSON.stringify()的作用是将 JavaScript 对象转换为 JSON 字符串,JSON.parse()可以将JSON字符串转为一个对象。

function deepClone(obj){
    let _obj = JSON.stringify(obj),
        objClone = JSON.parse(_obj);
    return objClone
}    
let a=[0,1,[2,3],4],
    b=deepClone(a);
a[0]=1;
a[2][0]=1;
console.log(a,b);

let arr = [1,2,3];
JSON.stringify(arr);//'[1,2,3]'
typeof JSON.stringify(arr);//string

let string = '[1,2,3]';
console.log(JSON.parse(string))//[1,2,3]
console.log(typeof JSON.parse(string))//object

在使用JSON.parse()需要注意一点,由于此方法是将JSON字符串转换成对象,所以你的字符串必须符合JSON格式,即键值都必须使用双引号包裹;

let a = '["1","2"]';
let b = "['1','2']";
console.log(JSON.parse(a));// Array [1,2]
console.log(JSON.parse(b));// 报错

JSON.stringify()的几种妙用

1.判断数组是否包含某对象,或者判断对象是否相等。

//判断数组是否包含某对象
let data = [
    {name:'echo'},
    {name:'听风是风'},
    {name:'天子笑'},
    ],
    val = {name:'天子笑'};
JSON.stringify(data).indexOf(JSON.stringify(val)) !== -1;//true

//判断两数组/对象是否相等
let a = [1,2,3],
    b = [1,2,3];
JSON.stringify(a) === JSON.stringify(b);//true

2.让localStorage/sessionStorage可以存储对象。

localStorage/sessionStorage默认只能存储字符串,而实际开发中,我们往往需要存储的数据多为对象类型,那么这里我们就可以在存储时利用json.stringify()将对象转为字符串,而在取缓存时,只需配合json.parse()转回对象即可。

//存
function setLocalStorage(key,val){
    window.localStorage.setItem(key,JSON.stringify(val));
};
//取
function getLocalStorage(key){
    let val = JSON.parse(window.localStorage.getItem(key));
    return val;
};
//测试
setLocalStorage('demo',[1,2,3]);
let  a = getLocalStorage('demo');//[1,2,3]

举报

相关推荐

0 条评论