JavaScript 数据类型 ( 深拷贝和浅拷贝 )

简单类型 ( 值类型 ) 和复杂类型( 引用类型

简单类型又叫做基本数据类型或者值类型,名值存储于栈内存中,String、Number、Boolean、null、undefined、Symbol、BigInt(ES10)

复杂类型又叫做引用类型( 名在栈内存中,值存在于堆内存中 ),在存储时变量中的存储仅仅是地址(  引用 ),通过 new 关键字创建的对象 (  系统对象、 自定义对象 ),如Object、Function、 Array 、Date 等        

堆和栈( JS 中没有堆栈概念 )

堆栈空间分配区别:

        1.栈 ( 操作系统 ):由操作系统自动分配释放存放函数的参数值、局部变量的值等。其操作方式类似于数据结构中的栈;简单数据类型存放到栈里面。

        2.堆 ( 操作系统 ):存储复杂类型,一般由程序员负责分配释放,若程序猿不释放,由垃圾回收机制回收;复杂数据类型存放到堆里面

内存分区

深拷贝和前拷贝 (面试题

// 相对完美的本递归实现深拷贝
const isComplexDataType = obj => (typeof obj === 'object' || typeof obj === 'function') && (obj !== null)
const deepClone = function (obj, hash = new WeakMap()) {
    if (obj.constructor === Date)
        return new Date(obj)       // 日期对象直接返回一个新的日期对象
    if (obj.constructor === RegExp)
        return new RegExp(obj)     //正则对象直接返回一个新的正则对象
    //如果循环引用了就用 weakMap 来解决
    if (hash.has(obj)) return hash.get(obj)
    let allDesc = Object.getOwnPropertyDescriptors(obj)
    //遍历传入参数所有键的特性
    let cloneObj = Object.create(Object.getPrototypeOf(obj), allDesc)
    //继承原型链
    hash.set(obj, cloneObj)
    for (let key of Reflect.ownKeys(obj)) {
        cloneObj[key] = (isComplexDataType(obj[key]) && typeof obj[key] !== 'function') ? deepClone(obj[key], hash) : obj[key]
    }
    return cloneObj
}

// 下面是验证代码

let obj = {
    num: 0,
    str: '',
    boolean: true,
    unf: undefined,
    nul: null,
    obj: { name: '我是一个对象', id: 1 },
    arr: [0, 1, 2],
    func: function () { console.log('我是一个函数') },
    date: new Date(0),
    reg: new RegExp('/我是一个正则/ig'),
    [Symbol('1')]: 1,
};

//设置 "不可枚举属性"
Object.defineProperty(obj, 'innumerable', {
    enumerable: false, value: '不可枚举属性'
}

);
obj = Object.create(obj, Object.getOwnPropertyDescriptors(obj))
// 设置loop成循环引用的属性
obj.loop = obj    

let cloneObj = deepClone(obj)
cloneObj.arr.push(4)
console.log('obj', obj)
console.log('cloneObj', cloneObj)

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值