Difference between let and var inside setTimeout?
我知道let和var的区别,let是块范围,var是功能范围。
1 2 3 4 5 6 7 8 9 | for(var i=0; i< 3; i++){ setTimeout(function(){ console.log(i); }, 10); } output : 3 3 3 |
我知道上面的代码片段是如何工作的(当i的值为3时,
但是
1 2 3 4 5 6 7 8 9 | for(let i=0; i< 3; i++){ setTimeout(function(){ console.log(i); }, 10); } output : 1 2 3 |
上面的代码片段让我困惑。据我所知,它应该抛出引用错误(因为执行
谁能解释第二个for循环如何在运行时工作?
这就是结束的魔力。在你的循环中
1 2 3 4 5 | for(let i=0; i< 3; i++){ setTimeout(function(){ console.log(i); }, 10); } |
您正在声明一个函数
1 2 3 | function(){ console.log(i); } |
此外,循环本身声明了一个块
1 2 3 4 | for(let i=0; i< 3; i++){ // this is a block scope because it is contained in // braces } |
用
由于闭包,您在循环中声明的函数可以访问其作用域和其父作用域中声明的所有变量,直到它被垃圾收集为止。
A closure is the combination of a function and the lexical environment
within which that function was declared. This environment consists of
any local variables that were in-scope at the time that the closure
was created.
创建
函数存在,直到您声明的间隔通过为止。这就是为什么在循环中声明的3个函数中的每一个都会打印
第二个例子(使用
有关函数关闭的更多信息,请参阅JavaScript闭包如何工作。
在此上下文中使用
1 2 3 4 5 6 7 | for (var i = 0; i < 3; i++) { (function (i) { setTimeout(function () { console.log(i); }, 10); })(i); } |