前言:深入js对学习框架很重要,希望这一系列文章会对你有帮助(持续更新中)
深入系列:深入javascript之原型和原型链
深入系列:深入javascript之执行上下文
一,作用域
包括静态作用域和动态作用域,静态作用域也叫词法作用域,javascript采用的是静态作用域。
js中作用域是指可访问变量,对象,函数的集合,也就是调用它们能生效的代码区块。在js中没有块级作用域,只有全局作用域和函数作用域,可以模仿块级作用域,下面会讲到。
1-1,全局,函数作用域
看个简单的例子
var a = 10
function f1(){
var b = c = 20;
console.log(a); //10
console.log(c); //20
function f2() {
console.log(b); //20
}f2();
}
f1();
console.log(a); //10
console.log(c); //20
console.log(b); //error
var b = c = 20 是指 var b = c; c = 20
在f1函数中c没使用var声明为全局变量,b为局部变量,绑定在f1函数下,外部访问不到。
1-2,模仿块级作用域
没有块级作用域,但是有if(),for()等块语句,在块语句内部定义的变量会保留在它们已经存在的作用域内,举个栗子:
if(true) {
var word = 'hello';
console.log(word); //hello
}
console.log(word); //hello
if()语句存在全局作用域下,所以内部定义的变量存在于全局作用域中,无论在哪都可以访问。
function add(num) {
if(num > 10) {
var num = 10;
console.log(num); //10
}
console.log(num); //10
}
add(11);
console.log(num); //Uncaught ReferenceError: num is not defined
此时if()在add函数中,内部定义的变量存在于add函数的作用域中,只有在函数和块语句中才可以访问到,外部无法访问。
使用自执行的匿名函数包裹块语句构建块作用域,也叫私有作用域
function add(num) {
for(var i = 0; i < num; i++) {
console.log(i); //0,1,2,3,4,5,6,7,8,9
}
console.log(i); //10
}
add(10);
将代码改为
function add(num) {
(function () {
for(var i = 0; i < num; i++) {
console.log(i); //0,1,2,3,4,5,6,7,8,9
}
})()
console.log(i); //Uncaught ReferenceError: i is not defined
}
add(10);
此时变量i只能在for()循环中访问到,在add函数和外部都无法访问,并且在匿名函数中定义的任何变量都会在执行结束时被销毁,所以变量i只能在for()循环中使用。
在ES6中新增了块级作用域,let const声明的变量在块语句中声明时,外部无法访问。