2012-08-13 37 views
7

局部范围我一直在使用Object-Oriented JavaScript by Stoyan Stefanov了解全球及在Javascript

他举了一个例子比较全局和局部范围内学习JavaScript:

var a = 123; 
function f() { 
    alert(a); 
    var a = 1; 
    alert(a); 
} 
f(); 

望着这个例子中,我预计第一警报是'123',第二个警报是'1'。你瞧,斯托扬说:

你可能想到的是,第一个警报()会显示123(的 值的全局变量),第二个会显示1(当地的一个)。 情况并非如此。第一个警报将显示“未定义”。这是 ,因为在函数内局部范围比全局范围更重要。因此,一个局部变量覆盖与 同名的任何全局变量。在第一次警报时()a尚未定义 (因此值未定义),但仍存在于本地空间中。

我的解释不清楚,局部变量如何覆盖第一个alert中的全局变量?任何其他/不同的解释将不胜感激。

回答

8

它不覆盖全局变量。发生的事情被称为“变量提升”。即,在函数的顶部插入var a;

脚本引擎改变你的脚本如下所示:

var a = 123; 
function f() { 
    var a; 
    alert(a); 
    a = 1; 
    alert(a); 
} 
f(); 

的教训:在使用之前务必声明变量。有些人会说在函数的顶部声明所有的变量。

+0

感谢胡安另一个例子。我在猜测,你会接受作者使用“覆盖”一词的问题吗?我开始认为如果我在函数之外调用alert(a),我会得到'123',这意味着没有覆盖,而是两个'a'变量,一个全局变量和一个局部变量。 – 2012-08-13 17:15:53

+3

覆盖不是正确的术语,局部变量**阴影**全局变量,但真正的问题是要明白,如果你在函数中的任何地方有一个'var',全局** **阴影**完整的功能,甚至在它宣布之前。 – 2012-08-13 17:16:56

+0

谢谢,这是有益的,并澄清 – 2012-08-13 17:21:07

1

简而言之,首先考虑变量和函数的所有声明。因此,本地var a实际上将仅覆盖局部范围内的全局变量,并且将不具有值,即undefined。所以首先警报将显示undefined。第二次警报将显示1,因为它在a = 1之后。这只发生在本地,全局变量a将具有值123 - 它不会被改变。

使用函数来显示它是如何工作

function show(){ 
    alert("I am global"); 
} 

function f() { 

    show(); 

    show = function(){ 
     alert("I am second"); 
    } 

    show(); 

    function show(){ 
     alert("I am first"); 
    } 

} 
f(); 
show(); 
+0

我不明白这个例子如何帮助了解变量提升,你甚至没有本地变量。答案中的单词似乎是正确的(尽管令人困惑),但这个例子使得这个额外的混淆 – 2012-08-13 17:20:34