美文网首页
前端的那些事(一):变量提升与函数提升

前端的那些事(一):变量提升与函数提升

作者: 沐雨芝录 | 来源:发表于2019-04-24 17:08 被阅读0次

    前言

    是不是经常遇到面试问你,为什么会变量提升,函数提升,它的行为又是什么?

    解答

    js程序编译有两个步骤:

    • 预解析 (就是执行上下文,有三类变量声明,函数声明和this,本文暂不讨论this,后续专门写)
    • 代码执行
    demo
    var a = 1;
    function a() {}
    a = 2;
    

    如上述demo中,其实真正解析成:

    var a;  // 第一步
    a = function () {}  // 第二步
    a = 1;  // 第三步
    a = 2; // 第四步
    
    

    第一步,变量声明提升a;第二步,函数提升,把函数赋值给a;第三步变量赋值a=1;第四步变量赋值a=2。

    \color{#FF0000}{结论}编译器对代码进行预解析,先将变量声明提升,再将函数提升,接下来就是引擎进行变量赋值。(记住,变量提升只是声明提升,赋值不提升,函数提升将提升到赋值之前。)


    隐式变量分配权重大

    demo
    function parent(a) {
      var b = 2;
      function a() {return 'a'}
      function b() {return 'b'}
      b = 3;
      return a + b;
    }
    console.log(parent(1)); // function a() {return 'a'} 3
    

    大家看到这个答案是不是很疑惑,不应该函数先提升,赋值后运行吗?为何return a +b 得到的是函数a + 3呢?
    解析上述demo:

    function parent() {
      var a;
      var b;
      a = 1;
      a = function() {return "a";};
      b = function() {return "b";};
      b = 2;
      b = 3;
      return a + b;
    }
    console.log(parent()); // function a() {return 'a'}3
    

    隐式变量分配在函数提升之前,所谓隐式变量分配在这里就是函数传递过来的值1。

    \color{#FF0000}{结论}编译器对代码进行预解析,先将变量声明提升,隐式变量分配提升(函数传值),再将函数声明提升,接下来就是js引擎让代码逐步执行。


    给大家出两道题:

    一、为何第一个num是undefined

    var num = 123;
    function foo1(){
        console.log( num );    //undefined
        var num = 456;
        console.log( num );    //456
    }
    foo1();
    

    提示:foo1函数提升了。

    二、为何打印1

    foo(); // 1
    var foo;
    function foo() { console.log( 1 );
    }
    foo = function() { console.log( 2 );
    }
    

    需要注意的是,遇到匿名函数(函数表达式)当成普通变量来处理,不要当成函数声明。


    更多内容可以看我的集录: 全面攻陷js:更新中...

    相关文章

      网友评论

          本文标题:前端的那些事(一):变量提升与函数提升

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