美文网首页
JavaScript中的堆与栈 、浅拷贝与深拷贝

JavaScript中的堆与栈 、浅拷贝与深拷贝

作者: 王乐城愚人云端 | 来源:发表于2019-03-06 17:55 被阅读0次

    1. 什么是堆栈

    在计算机领域中,堆栈是两种数据结构,它们只能在一端(称为栈顶(top))对数据项进行插入和删除,因而按照后进先出的原理运作。

    • 栈 stack:由编译器自动分配释放,存放函数的参数值,局部变量的值等。其操作方式类似于数据结构中的栈。
    • 堆 heap:一般由程序员分配释放, 若程序员不释放,程序结束时可能由OS回收。注意它与数据结构中的堆是两回事,分配方式倒是类似于链表。

    2. JavaScript中的基本类型和引用类型与堆栈的联系

    1. 基本类型:Undefined、Null、Boolean、Number 和 String,这5中基本数据类型可以直接访问,他们是按照值进行分配的,存放在栈(stack)内存中的简单数据段,数据大小确定,内存空间大小可以分配。
    2. 引用类型:即存放在堆(heap)内存中的对象,变量实际保存的是一个指针,这个指针指向另一个位置。

    内存

    栈 stack 内存 堆 heap 内存
    1
    "hello"
    true
    null
    undefined
    object1 {name: 'tom', age: 23}
    array1 [1,2,3]
    varible 23

    varible = object1.age 是引用,所以在堆中保存的是指针,在栈中保存的引用数据

    1. 最新的基本类型和引用类型,以及之间的区别。

    基本数据类型:按值访问,可操作保存在变量中的实际的值。基本类型值指的是简单的数据段。

    基本数据类型有这六种:undefined、null、string、number、boolean、symbol(es6)。

    引用类型:当复制保存着对象的某个变量时,操作的是对象的引用,但在为对象添加属性时,操作的是实际的对象。引用类型值指那些可能为多个值构成的对象。

    引用类型有这几种:Object、Array、RegExp、Date、Function、特殊的基本包装类型(String、Number、Boolean)以及单体内置对象(Global、Math)。

    3. 什么是浅拷贝,深拷贝

    1. 基本类型:Undefined、Null、Boolean、Number 和 String,这5中基本数据类型的拷贝,是直接在栈(stack)中增加新数据,拷贝前后互不相干,所以不存在浅拷贝和深拷贝
    2. 引用类型, 浅拷贝下,拷贝引用类型的属性时,是拷贝引用的指针,所以修改内容会影响原始对象。深拷贝下,拷贝引用类型的属性时,是拷贝内容,所以修改不影响原始对象。

    4. 手写浅拷贝,深拷贝

    浅拷贝一,for in

    function copy(obj){
        var newObj = {};
        for(var key in obj){
            newObj[key] = obj[key];
        }
        return newObj;
    }
    

    浅拷贝二, Object.keys

    function copy2(obj){
        var newObj = {};
        Object.keys(obj).forEach(key=>{
            newObj[key] = obj[key]
        })
        return newObj;
    }
    

    深拷贝一,最简单,但只支持符合JSON格式的

    function deepCopy(obj) {
        return JSON.parse(JSON.stringify(obj));
    }
    

    深拷贝二,(推荐)基本类型直接赋值,对象分三种情况,null, array,object,函数方法直接赋值

     function deepCopy(obj){
        var o;
        switch(typeof obj){
        case 'undefined': break;
        case 'string'   : o = obj + '';break;
        case 'number'   : o = obj - 0;break;
        case 'boolean'  : o = obj;break;
        case 'object'   :
            if(obj === null){
                o = null;
            }else{
                if(obj instanceof Array){
                    o = [];
                    for(var i = 0, len = obj.length; i < len; i++){
                        o.push(deepCopy(obj[i]));
                    }
                }else{
                    o = {};
                    for(var k in obj){
                        o[k] = deepCopy(obj[k]);
                    }
                }
            }
            break;
        default:
            o = obj;break;
        }
        return o;
    }
    

    深拷贝三,缺点,只支持拷贝对象

        function deepCopy(obj, clone) {
          clone = clone || {}
          for (const key in obj) {
            if (obj.hasOwnProperty(key)) {
              if (typeof obj[key] === 'object') {
                clone[key] = Array.isArray(obj[key]) ? [] : {}
                deepCopy(obj[key], clone[key])
              } else {
                clone[key] = obj[key]
              }
            }
          }
          return clone
        }
    

    相关文章

      网友评论

          本文标题:JavaScript中的堆与栈 、浅拷贝与深拷贝

          本文链接:https://www.haomeiwen.com/subject/typxpqtx.html