JavaScript,作用域链和模拟块级作用域(笔记二)

          JavaScript的作用域,让我大吃一斤,没看到还不知道,竟然还有这些注意的地方。

   1、对JavaScript作用域的不了解

          对很多人应该来说,这个不是问题,但刚刚学习JavaScript的人来说,这应该算是一个细节的忽略。

直接上代码:

JavaScript,作用域链和模拟块级作用域(笔记二)_第1张图片

         对于之前学习其他语言的人来说,***竟然还有这种情况

JavaScript,作用域链和模拟块级作用域(笔记二)_第2张图片

        图为java代码

        由上就可以看出,在JavaScript中是没有块级作用域的。那么JavaScript不是无法无天了吗。

   2、JavaScript的作用域环境和作用域链

        本人对JavaScript的理解,就作用域环境而言,个人认为它就是相当于块级作用域,不过它只包含两个方面:全局环境和函数环境。

        所以可以简单的理解成,JavaScript就函数的花括号{  }有用。

        在确认环境的范围后,就可以去理解作用域链的关系。(这里就简单的笔记,详细看《高程3》)

        作用域链,个人理解,就是在JavaScript中每次运行代码时,都会有一个环境。

        JavaScript,作用域链和模拟块级作用域(笔记二)_第3张图片

         在这个简单的代码中就,是在一个环境中执行,而这个环境就是全局环境(在window中就是window)

         这是就会产生一条作用域链,这条作用域的前端在window中就是window对象。如图

        JavaScript,作用域链和模拟块级作用域(笔记二)_第4张图片


        椭圆形用来代表环境,箭头代表作用域链。

        在系统运行到函数的时候,这个时候,作用域的环境就是函数的环境,而作用域链在链接完这个环境后回去寻找,它外层的环境,直到寻找到全局环境。


JavaScript,作用域链和模拟块级作用域(笔记二)_第5张图片

        这里就有一个简单的函数XXX,这时就存在两个环境。

        然后我们运行XXX函数。

        注:这里说一个应该基础不能再基础的问题,function是定义函数,不运行函数时(给像我一样的菜鸟),所以我们调用函数

       JavaScript,作用域链和模拟块级作用域(笔记二)_第6张图片


         或直接运行

               JavaScript,作用域链和模拟块级作用域(笔记二)_第7张图片 


     这个时候的作用域链就是:

JavaScript,作用域链和模拟块级作用域(笔记二)_第8张图片

    arguments[ ]数组是function的参数(这里就要说到,在JavaScript中函数参数的接受与参数的定义无关,函数有一个自带的数组接收参数,关于函数参数下次笔记里全面的回顾一下,写一下)。

    所以在JavaScript执行时当前的环境,需要的识别符(如i,j)回先去当前环境寻找,有没有定义,有的话停止寻找,没有的话接着到下一个环境去寻找直到全局环境,如果都没找到就报错。

3、模拟块级作用域

   在ECMAScript 6(简称ES6)中新增了一个“let”使js有了与块级作用域一样的功能。

   在没有块级作用域时:

    JavaScript,作用域链和模拟块级作用域(笔记二)_第9张图片

    i本来应该在for循环里才比较合适,现在它循环好后就直接出来了。

    如果这个时候用let代替

       JavaScript,作用域链和模拟块级作用域(笔记二)_第10张图片

     就会被报错。

 4、一种不推荐的注意点

     JavaScript是一种灵活的语言,在定义一下类型的时候,一定要注意。

     在JavaScript

JavaScript,作用域链和模拟块级作用域(笔记二)_第11张图片

     由于函数作用域环境的影响,在全局环境中的“i”是找不到定义的,所以报错。但是如果你去掉var的话

JavaScript,作用域链和模拟块级作用域(笔记二)_第12张图片

     现在应该大致知道了,去掉var后i就变成了全局变量。(但这里不推荐这样用!)

  

你可能感兴趣的:(JavaScript,笔记)