2017-09-01 46 views
0

我正在阅读'范围&'系列'你不知道JS'中的书'闭包',并且我看到函数首先被挂起,然后被挂起。 经历此代码段:词汇范围问题

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

如果是这种情况下,应在函数bar()不被提升到顶部和此代码应产生错误?由于吊装后,此代码应该是这样的(至少我的理解)

function foo() { 
    function bar() { 
     console.log(a); 
    } 
    var a; 
    a = 2; 
} 

这是因为功能提升到顶部,后来变量。如果情况并非如此,请纠正我。

+0

'console.log(a)'直到调用bar()时才会执行。它不会尝试访问'a'直到那个时候,所以'var a;'在任何尝试调用bar()之前都会被处理很久。 –

回答

2

他们都悬挂一路顶,所以a所在范围内bar;这不是函数是“高于”变量。订单起作用的唯一时间是函数声明和变量具有相同的名称,在这种情况下,函数声明胜出,因为当变量被提升时,如果已经存在与给定名称的现有绑定,则不会创建函数声明。

“提升”是一个方便的速记术语,但它不是字面的。当foo被称为(留出细节的公平位专注于问题的问题)是会发生什么:

  1. 执行上下文是为调用创建foo
  2. 对象在此背景下被创建的用于识别(在你的例子一样bara),用于这方面的执行“绑定”
  3. 所有函数声明进行处理,并为他们的标识绑定添加到对象(如果有多个declara具有相同名称的系统蒸发散,最后一个胜)
  4. 所有变量声明进行处理,它们的标识符被添加到该对象如果对象还没有为他们

绑定该对象则用于处理执行上下文中的绑定(例如,当引用a时使用与绑定关联的值,并且当设置a等时设置)。

0

hoisting在汇编部分和编译bar期间完成,直到它被调用才会完成功能。那么为什么bar应该显示错误。 如果您还想了解有关javascript如何编译或执行的详细信息。这是一个不错的视频https://www.youtube.com/watch?v=QyUFheng6J0