变量提升

一、栈内存 和 堆内存
栈内存:Undefined、boolean、string、number和null。这五种数据类型可以直接访问,是按照值进行分配的,存放在栈内存当中。

堆内存:引用类型存放在堆内存中的对象,变量保存的实际上是一个指针,这个指针指向一个位置。

堆内存的释放:让所有引用堆内存空间地址的变量赋值为NULL即可(没有变量占用这个堆内存了,浏览器会在空闲的时候把它释放掉。)
栈内存的释放:一般情况下,当函数执行完成,所形成的私有作用域(栈内存),都会自动释放掉。(在栈内存中存储的基本值也都会被释放掉),但是也有特殊不销毁的情况:
    a:函数执行完成,当前形成的栈内存中,某些内容被栈内存以外的变量占用了,此时栈内存不能释放(一旦释放,外面就找不到原有的内容了。)
    b:全局栈内存只有在页面关闭的时候被释放掉。
    c:如果当前栈内存没有被释放,那么之前在栈内存中存储的基本值也不会被释放,能够一直保存下来。

二、变量声明提升
1.变量提升即把变量提升到最前面,在全局中,有 var 的先放在前面,随后再进行相应的赋值。

2.有 var 和 无var 的区别:

        1.在全局中有 var 的本质是变量,不加 var 是window下的属性  ---> a = 12 ---> window.a = 12

3.在私有作用域(函数内部)中 有var 和无 var的区别

        1.带var 的在私有作用域变量提升阶段,都声明为私有变量,和外界没有任何关系。
        2.不带var 的,不是私有变量,会向上级作用域查找,看是否为上级的变量,不是,继续向上查找,一直找到window为止(这种查找机制为:作用域链) 。也就是我们在私有作用域中操作的非私有变量,是一直操作别人的。
        3.全局作用域的不可以拿到私有作用域的东西,就好像父亲一般不会问儿子拿钱。
        4.在作用域查找过程中,假如window也没有这个变量,就相当于给window设置了一个新的属性。

三.在有判断语句的情况时:

1.在当前作用域下,不管判断条件是否成立,都要进行变量提升。
                    1.带var 的只是声明变量
                    2.带function的在老版本中,声明+定义都会处理,新版本则只会声明。

四、当遇到重名问题的时候:

1.带var 和 function 关键字声明想用的名字,这种也算是重名了(其实是用一个变量,只是存储的值的类型不一样了)
2.关于重名的处理:如果名字重复了,不会重新的声明,但会重新定义(重新赋值),不管是代码提升还是代码执行阶段皆是如此。

五、ES6中不存在变量提升:

1.在ES6中基于let/const等方式创建变量或者函数,不存在变量提升机制
2.切断了全局变量和window属性的映射机制
3.在相同的作用域中,基于let不能声明相同名字的变量,不管用什么方式,在当前作用域下声明了变量,再次使用let创建都会报错。--> a = 12 ;  let a =12;
4.虽然没有变量提升机制,但是在当前作用域自上而下执行之前,浏览器会做一个重复性检测:自上而下查找当前作用域下所有变量,一旦发现有重复的,直接抛出异常,代码也不会执行。(虽然没有把变量提前声明定义,但是浏览器已经记住了当前作用域下有哪些变量)。

六、全局变量和私有变量:

  1. 在私有作用域中,只有以下两种情况是私有变量:
    a:声明过的变量(带var /function)
    b:形参也是私有变量
    剩下的都不是自己的私有变量,都需要基于作用域链的机制向上查找。

    2.当前函数执行,形成一个私有作用域A,A的上级作用域是谁,和他在哪执行是没有任何关系的,只和他在哪里创建(定义)的有关系。在哪里创建,它的上级作用域就是谁。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值