作用域和闭包
js 执行上下文
当我们启动程序时,我们从全局执行上下文中开始。
一些变量是在全局执行上下文中声明的。我们称之为全局变量。
当程序调用一个函数时发生以下几个步骤:
- JavaScript创建一个新的执行上下文,我们叫作本地执行上下文。
- 这个本地执行上下文将有它自己的一组变量,这些变量将是这个执行上下文的本地变量。
- 新的执行上下文被推到到执行堆栈中。可以将执行堆栈看作是一种保存程序在其执行中的位置的容器。
词法作用域(Lexical scope)
JavaScript的一个复杂之处在于它如何查找变量,如果在函数执行上下文中找不到变量,它将在调用上下文中寻找它,如果在它的调用上下文中没有找到,就一直往上一级,直到它在全局执行上下文中查找为止。(如果最后找不到,它就是 undefined)。
一个函数可以访问在它的调用上下文中定义的变量,这个就是词法作用域(Lexical scope)。
闭包
它是这样工作的,无论何时声明新函数并将其赋值给变量,都要存储函数定义和闭包。闭包包含在函数创建时作用域中的所有变量,它类似于背包。函数定义附带一个小背包,它的包中存储了函数定义创建时作用域中的所有变量。
我将永远记住闭包的方法是通过背包的类比。当一个函数被创建并传递或从另一个函数返回时,它会携带一个背包。背包中是函数声明时作用域内的所有变量。