2016-07-23 78 views
1

在下面的代码:Javascript:为什么具有全局执行上下文的回调函数可以访问范围变量?

function test() { 
    var x = 5 // scoped to test function 
    console.log(this); // global object 
    logCb(function(){ 
     console.log(this); // global object 
     console.log(x); 
    }) 
} 

function logCb (cb) { 
    console.log(this); // global object 
    cb() // This still seems to execute within the test function scope? why... 
} 

test() 

x被作用域进行测试,这是回调函数被定义在哪里。因为logCb()函数不能访问x变量,所以我会预计行cb()会抛出一个错误。

但事实并非如此。为什么?看起来回调函数中的引用是在赋值过程中创建的,而不是在执行过程中创建的 - 如果您考虑提升 - 即在编译过程中,回调函数被提升到“test”的顶部,然后赋值在测试中发生范围?

我已经读过,执行与作用域不一样。在本文中:http://ryanmorr.com/understanding-scope-and-context-in-javascript/,这句话scope pertains to the variable access of a function when it is invoked and is unique to each invocation似乎暗示回调是从测试函数中调用的。

因为在我看来,不管在哪里调用回调函数,它仍然会被测试范围。

我想我的问题是:

如何在回调函数中定义的条款来处理,然后考虑范围和执行上下文时调用?

+0

你有没有听说过在JavaScript关闭? –

+0

函数的作用域是基于它声明的地方,而不是从那里调用的地方。函数的'this'与范围无关,并且基于* how *函数被调用。 – nnnnnn

+0

@RajaprabhuAravindasamy。所以回调已经结束了测试? –

回答

1

在思考范围和执行上下文时,如何根据定义处理回调函数,然后调用 ?

一个功能范围是基于它是在词法环境实际存在

说明:回调功能测试()词汇存在,所以它总是试图找到内本身的任一值(如果存在的话),否则它会看到其在外部环境

值(其为功能测试在这种情况下) 测试功能LogCb功能将遵循相同的做法。在这种情况下,外部环境将全球

如何发动机跟踪范围分头执行 背景?

词法环境:东西在哪里坐在身在你写的代码。

执行上下文:包装帮助管理正在运行的代码。

现在在你的代码中有很多词法环境。哪一个当前正在运行通过执行上下文进行管理。它可以包含超出您在代码中编写的内容的内容。

每当执行上下文被创建,我们有三样东西是提供给我们:

  1. 全局对象(窗口):在全球范围内的任何变量或函数被链接到窗口对象
  2. “这个”
  3. 外环境

所以取决于哪个执行上下文当前正在运行,这些东西会按照它在哪里物理或词法存在于代码变化。例如,对于cb外环境是function test()

+0

引擎如何跟踪范围与执行上下文分开? –

1

范围由其中一个功能是创建,而不是由其中它被称为确定。

您传递给logCb的功能是在test内部创建的,所以它可以访问test的范围。

+0

您是否知道解释Google V8引擎如何执行此操作的好方法? –

1

当在javascript中调用某个函数时,会将一个上下文传递给它。

上下文可使用新是通过以下方式

  1. 一个,创建一个临时对象,并将其作为上下文传递给函数

  2. 经由对象a.getValue调用函数( )。的getValue获取上下文

  3. 如果没有上述2通过全局对象,即窗口