函数作用域[scope]

  • 外部对内部可见;
  • 内部对外部不可见;
  • 内部优先

JS中只有函数级别的作用域,没有块级别的作用域;换句话说,只有在进入或者退出函数的时候,作用域会发生变化。

1、外部对内部可见

<script>
    var scope='g';
    function t(){
        console.log(scope);
        // var scope="l";
        console.log(scope);
    }
    t();
</script>
结果 g g

2、内部堆外部不可见

<script>

    function t(){
        var scope="l";

    }
    t();
    console.log(scope);
</script>

3、都可见时,内部优先

<script>
    var scope='g';
    function t(){
        console.log(scope);
        var scope="l";
        console.log(scope);
    }
    t();
</script>

4、JS的作用域,都是函数级别的。

<script>
    var scope='g';
    if(true){
        var scope="l";
        console.log(scope);
    }
    console.log(scope);
</script>  //如果C或C++ 最后一个console 结果时g,
    for(var i=0;i<10;i++){

    }
    console.log(i); //10

执行环境和作用域链

执行环境(execution context),定义了执行期间可以访问的变量和函数。

1、全局执行环境

  • Global Object(window)
  • 从见到js代码开始创建
  • 到网页关闭时销毁

2、函数执行环境

  • Activation Object
  • 从函数调用开始创建
  • 到函数调用结束时销毁

执行环境(EC)和作用域链

1、作用域[scope],每个函数都有。

2、作用域是自由属性,只能由JS引擎访问。

3、作用域链,是AO和GO构成的链

4、所谓执行环境,就是根据作用域链一次查找变量和函数。

  • 找到即停;
  • 全部找完无果,报错。

5、作用域链每个函数都有

每个函数在定义(函数声明\函数表达式)时会拷贝其父亲函数的作用域链;

在函数被调用时,生成AO然后将AO压入作用域链的栈顶。

图

执行fa()函数时

图

执行fb()时

图

<script>
 //函数多次调用时,时产生相同的AO还是不同的AO?
  //  答:不同;
//函数递归调用时,时产生相同的AO还是不同的AO?
    //答:不同;
</script>

其他生成作用域链的方式

with,生成行的with variable object ,放在作用域链表顶端

图

    person={
        name:"yhb",age:22,height:175,
        wife:{name:"lwy",age:21}
    }
    with(person){
        console.log(name);
    }
     with(person.wife){
     console.log(name);
    }

作用域链的注意点

效率:尽量少使用靠近上层的变量。多使用自己局部的变量。

重名,容易出错:尽量减少不同层次函数使用相同的变量名。避免函数名与变量名一样

Last modification:January 30, 2020
如果觉得我的文章对你有用,请随意赞赏