做用域是指程序源代码中定义变量的区域。
做用域规定了如何查找变量,也就是肯定当前执行代码对变量的访问权限。
JavaScript 采用词法做用域(lexical scoping),也就是静态做用域。
想了解更多关于做用域的问题推荐阅读《你不知道的JavaScript上卷》第一章(或第一部分),
从编译原理的角度说明什么是做用域。归纳的说做用域就是一套设计良好的规则来存储变量,而且以后能够方便地找到这些变量。
复制代码
在你不知道的javascript上卷中是这样定义的:词法做用域就是定义在词法阶段的做用域。换句话说,词法做用域是由你在写代码时将变量和块做用域写在哪里来决定的,所以当词法分析器处理代码时会保持做用域不变(大部分状况下是这样的)。javascript
在JS中词法做用域的规则:java
例1bash
var a = 2;
function foo() {
var a = 3;
console.log(a); // 3
}
foo();
复制代码
例2函数
function foo() {
console.log(a); // 2
}
function bar() {
var a = 3;
foo();
}
var a = 2;
bar();
复制代码
只有函数才能制造做用域结构,那么只要是代码,至少有一个做用域,即全局做用域。ui
凡是代码中有函数,那么这个函数就构成另外一个做用域。若是函数中还有函数,那么在这个做用域中就又能够诞生一个做用域,那么将这样的全部做用域列出来,能够有一个结构:函数内指向函数外的链式结构。spa
以上面例2:设计
function foo() {
console.log(a); // 2
}
function bar() {
var a = 3;
foo();
}
var a = 2;
bar();
复制代码
做用域是由代码写在哪里决定的,而且是逐级包含的。code
咱们用级链来表示一下以上代码块:cdn
因此不管函数在哪里被调用,也不管它如何被调用,它的词法做用域都只由函数被声明时所处的位置决定。blog
var scope = "global scope";
function checkscope(){
var scope = "local scope";
function f(){
return scope;
}
return f();
}
checkscope();
复制代码