for(let i=0;i<2;i++){
setTimeout(function(){
console.log(i)
},100
);
}
for(var i=0;i<2;i++){
setTimeout(function(){
console.log(i)
},100
);
}
结果:0 1 2 2
①Js是单线程的,Settimeout是异步宏任务,所以代码执行遇到异步的,就放在事件队列中的,等线程中的任务执行完后才会执行事件队列中的任务。
② let是es6中声明变量的方式,有自己的作用域块,可以放变量,所以let绑定for循环时,每个i都有自己的值. 在这个for循环中就是满足一次条件向事件队列中添加一个打印i的事件,且每个事件中的i有自己的值.
③Var没有作用域块,for循环的变量就会后一个覆盖前一个,当循环完毕时i就只有一个值,又因为for循环的判断条件是不满足跳出,所以i最后是2而不是1 。
第一个:let将i绑定到for循环快中,事实上它将其重新绑定到循环体的每一次迭代中,确保上一次迭代结束的值重新被赋值。setTimeout里面的function()属于一个新的域,通过 var 定义的变量是无法传入到这个函数执行域中的,通过使用 let 来声明块变量,这时候变量就能作用于这个块,所以 function就能使用 i 这个变量了;输出为0,1.
第二个:settimeout是异步执行,1s后往异步任务队列里面添加一个任务,只有同步的全部执行完,才会执行异步任务队列里的任务,当主线执行完成后,i是2,所以此时再去执行任务队列里的任务时,所以输出两次2.