“当调用函数时闭包所指向的作用域链和定义函数时的作用域链不是同一个作用域链”,这句话怎么理解

1 1 收藏


直接登录
最新评论
  • itfinally Java猿 01/18 精华评论

    不是很理解你这句话,不知道在哪里看的。我来说说我的理解。

    比如在 A 函数内定义了 B 函数并通过 return 返回 B 的场景。
    实际上 B 函数的作用域链如下:
    function B         ——->    function A
    —————       |           —————–
    var a;                |               var _1;
    var b;                |               var _2;
    var c                 |               var _3;
    …                      |               …
    env ————–|              env ———–> window ( 如果 A 函数是 window 内定义情况下 )

    以上  , env 是什么鬼? 这是一个内部维护的一个引用外部环境的指针,如果是闭包,比如

    B 函数,外围还有个 A 函数的,那么此时 env 会指向 A 函数的环境,A 函数由于是直接在 window 定义的,所以 A 函数的 env 指向了 window 域。

    具体描述,在《JavaScript高级程序设计》( 第3版 ) 的作用域链一节中有描述。

    此处可以引申出比较多的有意思的东西,但也很容出现内存泄漏的情况。

    以上。

    • 天~田野 前端开发 01/19

      在JavaScript权威指南里,对作用域链有如下部分介绍:在JavaScript的顶层代码中,作用域链由一个全局对象组成。在不包含嵌套的函数体内,作用域链上有两个对象,第一个是定义函数参数和局部变量的对象,第二个是全局对象。在一个嵌套的函数体内,作用域链上至少有三个对象。当定义一个函数时,它实际上保存了一个作用域链。当调用这个函数时,它创建一个新的对象来存储它的局部变量,并将这个对象添加至保存的那个作用域链上,同时创建一个新的更长的表示函数调用作用域的“链”。对于嵌套函数来讲,事情变得更加有趣,每次调用外部函数时,内部函数又重新定义一遍。因为每次调用外部函数的时候,作用域链都是不同的。内部函数在每次定义的时候都有微妙的差别—在每次调用外部函数时,内部函数的代码都是相同的,而且关联这段代码的作用域链也不相同。

      关于以上这段描述,我不知道该如何理解才准确

       

      • itfinally Java猿 01/19

        其实就是我第一个回复的意思,就是表达方式不一样罢了,幸亏我第一本书不是犀牛书,这种描述说的….    如果我不懂的话,也会给绕进去。

        它的意思就是每个函数都是一个独立环境,除了有当前环境内所有变量的引用,还会有一个外部环境的引用,而且对于每个函数而言,他们的作用域链都不一样。

         

        什么是作用域链?我第一份回复就已经有了, A 和 B 函数下面那一串就是。

        你觉得他们各自的变量是相同的不?

        • 天~田野 前端开发 01/19

          当然不同了,在b作用域链上可以查找到a函数的变量,而在a函数作用域链上查找不到b函数的变量,因为a作用域链上没有那个保存b函数变量的对象,而b作用域链上有那个保存a函数变量的对象。我这样理解对不对呀。

          还有,上面写的“当调用这个函数时,它创建一个新的对象来存储它的局部变量,并将这个对象添加至保存的那个作用域链上,同时创建一个新的更长的表示函数调用作用域的“链”。”这句话中的下半句中的这个“链”是指你所说的外部环境的引用吗?

          如果是这样的话,那这和闭包怎么关联了