zoukankan      html  css  js  c++  java
  • 变量提升

    作用域的一些概念

    任何声明在某个作用域内的变量,都将附属于这个作用域。

    提升

    先看两个例子
    eg1

    a = 2;
    var a;
    console.log( a );   //2
    

    eg2

    console.log(a);
    var a=2; //undefined
    

    对于eg2 js会将其看成两部分,var a ,a=2;所以eg2会变为

    var a;
    console.log(a);
    a=2;
    
    原因

    引擎在解释js代码之前首先对其进行编译。编译阶段的一部分工作就是找到所有的声明,并用合适的作用域将它们关联起来。
    只有声明本身会被提升,而赋值或其他运行逻辑会留在原地。

    • 函数声明会被提升,但是函数表达式不会被提升
    foo();
    var foo=function bar(){
      //...
    };
    

    这段中变量标识符foo()先被提升并分配给所在作用域,但是foo并没有被赋值,此时foo()是undefined,此时对undefined值进行操作而导致非法操作,抛出TypeError异常。

    var foo;
    foo();
    foo=function bar(){};
    
    • 即使是具名函数表达式,名称标识符在赋值之前也无法在所在作用域中使用;
    foo();//TypeError;
    bar();//ReferenceError;
    var foo=function bar(){
    //...
    };
    

    经过变量提升的形式:

    var foo;
    foo();
    bar();
    foo=function(){
       var bar=...self...
      //...
    };
    
    • 函数优先
      函数声明和变量声明都会被提升,在多个重复声明的代码中,函数首先被提升,然后是变量;
      且后面的可以覆盖前面的;
    foo();//3
    function foo(){
    console.log(1);
    }
    var foo=function(){
    console.log(2);
    };
    function foo(){
    console.log(3);
    }
    

    总结

    预编译:函数声明整体提升,变量声明提升(赋值不提升)。
    几个概念:
    1.暗示全局变量(implyglobal):变量未经声明就赋值,此变量属于全局变量。
    2.一切声明的变量,都是全局的属性
    作用域做题四部曲:
    1.创建AO对象(作用域、执行器上下文)
    2.找形参和变量声明,将其作为AO对象的属性名,值为undefined
    3.形参和实参相统一
    4.在函数体里找函数声明,将值赋予函数体。
    (var b=function(){}叫函数表达式 不在考虑里)预编译出现在函数声明的前一刻

    题:

    function fn(a){
    	console.log(a);
    	var a = 123;
    	console.log(a);
    	function a(){}
    	console.log(a);
    	var b= function(){}
    	console.log(b);
    	function d(){}
    }
    fn(1);
    //function a(){}
    //123
    //123
    //function (){}
    

    在这里插入图片描述
    步骤三:

    AO{
    a:function a(){},
    b:undefined,
    d:function d(){}
    }
    

    再按照顺序执行。

    参考:你不知道的JaveScript上卷——提升

  • 相关阅读:
    postman简单使用
    Jenkins新建任务
    Property 'mapperLocations' was not specified or no matching resources found org.apache.ibatis.builder.BuilderException: Could not find value method on SQL annotation
    spring boot 处理异常
    Spring MVC @ExceptionHandler Example【转】
    微信小程序bindtap与catchtap的区别【转】
    Android imageview点了二,三次才有效果处理
    android 发email
    startActivity报错exposed beyond app through Intent.getData()
    ENUM 值.ordinal() 获取index
  • 原文地址:https://www.cnblogs.com/xmjs/p/14019897.html
Copyright © 2011-2022 走看看