ES6块级作用域
ES5中,没有块级作用域,所以会出现以下情况:
var callbacks = [];
for(var i=0;
i<=2;
i++){
callbacks[i] = function(){
return i * 2;
}
}console.table([
callbacks[0](),
callbacks[1](),
callbacks[2](),
])
这段代码的结果是输出3个6。
首先var i=0这一句话,将i做了一个变量提升,i是一个跟callbacks平级的变量;
然后进行for循环,for 循环结束时,i的值已经被更新成为了3;
由于function(){return i*2}不是立即被调用的,而是循环结束后,也就是i等于3的时候才调用的,它执行的时候会去找它上一级作用域中i的值,发现i等于3,于是进行计算并输出,所以
callbacks[0]()
,callbacks[1]()
,callbacks[2]()
的结果全部都是6。ES6中我们可以用let来声明变量,将变量的作用域限定为块级作用域,不存在变量提升:
const callbacks = [];
for(let i=0;
i<=2;
i++){
callbacks[i] = function(){
return i * 2;
}
}console.table([
callbacks[0](),
callbacks[1](),
callbacks[2](),
])
结果为0,2,4。
let声明的变量为块作用域,作用于当前块;每次循环都会把值保留下来供后面的闭包使用。
这段for循环等价于:
for (let i = 0;
i < 10;
i++) {
a[i] = (function(i) {
return function(){
console.log(i);
}
})(i);
}
在ES6中只需一个花括号就可以指定块作用域。
{
function foo(){
return 1;
}
console.log(foo() === 1);
{
function foo(){
return 2;
}
console.log(foo() === 2);
}console.log(foo() === 1);
}
【ES6块级作用域】结果是打印3个true。
可见两个作用域没有相互影响,一对花括号就已经把作用域隔离。
推荐阅读
- (二)ES6第一节变量(let|(二)ES6第一节变量(let,const)
- 六步搭建ES6语法环境
- 前端|web前端dya07--ES6高级语法的转化&render&vue与webpack&export
- arrow|arrow function
- 1.块级作用域绑定
- es6官方文档
- Solidity|Solidity - 变量作用域
- 如何理解es6中的class,以及class中的constructor函数
- JavaScript作用域链
- 最简洁的代码实现数组去重