【问题标题】:Local variable impact global variable - Javascript variable scoping [duplicate]局部变量影响全局变量 - Javascript变量范围[重复]
【发布时间】:2012-11-05 19:28:14
【问题描述】:

可能重复:
variable hoisting

    var a = "global";

    //version 1
    function changeGlobal(){
        alert(a); //why is 'a' undefined here?
        if(a){ 
        var a = "local";
        alert(a);
        }
    }
    //version 2
    function changeGlobal(){
        alert(a); //why is 'a' 'global' here? what diff does 'var a="local"' make?
        if(a){ 
        //var a = "local";
        alert(a);
        }
    }
    changeGlobal();

问题是内联的。帮助我理解变量范围。

【问题讨论】:

  • 这不是那个问题的重复,“变量提升”,它说明了“全局范围”并展示了实现异常,尽管它是相关的。
  • @jAndy 有很多 JS 问题,在问这个问题之前我试着看一下 Couple。另外,我正在阅读“Alexei White”的“javascript”一书,他从未谈到提升。
  • 为什么你的函数有相同的名字,为什么var a = 'local'在后者中被注释掉了?我们应该如何确定调用哪些函数以及设置变量的顺序?

标签: javascript


【解决方案1】:

在 javascript 中,变量声明被“提升”到函数的顶部,与声明它们的位置无关。

所以在 changeGlobal 的第一个变体中,当您声明 var a = "local" 时,a 变量声明被提升到顶部。变量的赋值也没有被提升,所以当你提醒a时,它是一个未赋值的变量,因此是未定义的。

也就是说,

function changeGlobal(){
    alert(a); //why is 'a' undefined here?
    if(a){ 
    var a = "local";
    alert(a);
    }
}

等价于

function changeGlobal(){
    var a;    // hoisted here (not assigned a value yet)
    alert(a); //why is 'a' undefined here?
    if(a){ 
    a = "local"; // only assigned a value here
    alert(a);
    }
}

【讨论】:

    【解决方案2】:

    在版本 1 中,您声明了一个名为 a 的局部变量,该变量优先于 changeGlobal 函数中的全局 a。尽管它是在alert(a); 调用之后定义的,但它的定义被“提升”到范围的开头,但直到var a = "local"; 行才被初始化。这就是alert(a); 显示undefined 的原因。

    在版本 2 中,因为没有本地 a,所以您总是在处理全局 a,它在函数运行之前已经初始化。

    【讨论】:

      【解决方案3】:

      JavaScript 具有词法作用域,其中变量可以从它所在的程序/函数中取消引用 vared,然后向下(如引用它不会抛出 ReferenceError
      var 语句也将被提升,初始值设置为undefined

      或者用外行的话来说,变量的作用域是定义它们的函数,并且所有变量在函数执行期间的任何时候都可用,尽管可能尚未分配值。

      结合起来,这就是您所观察到的 - 一个局部 var 遮蔽了全局 var。

      【讨论】:

      • 我会说“函数作用域”(因为 ECMAScript 没有块作用域,这通常与词法作用域相关联)并省略“取消引用”的使用(这甚至意味着什么!?!) .术语 ReferenceError 源于变量/属性语法结构在内部分解为“引用”(根据规范),但不应与“需要取消引用以供使用”相混淆。
      猜你喜欢
      • 1970-01-01
      • 2014-09-17
      • 2018-09-02
      • 1970-01-01
      • 1970-01-01
      • 2013-05-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多