最近在刷js细节题的时候,经常遇到这么一些题
for(var i=0;i<5;i++){
setTimeout(function(){
console.log(i)
},1000)
}//输出结果是5个5
for(var i=0;i<5;i++){
(function(i){
setTimeout(function(){
console.log(i)
},1000)
})(i)
}//输出结果是0 1 2 3 4
for(var i={j:0};i.j<5;i.j++){
(function(i){
setTimeout(function(){
console.log(i.j)
},1000)
})(i)
}//输出结果是5个5
为什么有时输出5个5,有时输出0 1 2 3 4呢?
首先我们看第一例子,等主进程执行完后再执行setTimeout中的函数,到主进程执行完后,函数中使用的i仍然是for循环中一开始定义的i,也就是说执行console.log(i)语句时编译器会去拿i的值,这时i的值已经变成了5,所以输出来的是5个5。
再来看第二个例子,同样是等主进程执行完后再执行setTimeout中的函数,但不一样的是,setTimeout外层多了一个自调用函数,for循环中定义的i会先传值给自调用函数中的i,具体看图
第三个例子,由于js中数组和对象类型作为函数参数时,是传地址而不是传值,自调用函数并没有申请新的内存空间存储i值