首先定义一个数组 在for循环中使用定时器输出数组
1 var messages = ['1', '2', '3', '4']; 2 for (var i = 0; i < messages.length; i ++) { 3 setTimeout(function(){ 4 console.log(messages[i]); }, i*1000); 5 }
执行输出的是4个undefined
为什么不是输出 1 2 3 4 呢 而是输出underfined,这个问题期初以为是作用域的问题,最后百度了,终于找到其原因。
原因:setTimeout 使函数延迟1s执行,而for循环执行完成还不到0.1秒,到执行函数的时候,其实 i 已经变成4了,而数组下标最大数字是3,没有对应的数组值,所以为underfined。
解决方法 1
使用let定义变量I,不要使用var。let
语句声明一个块级作用域的本地变量,并且可选的将其初始化为一个值。
1 var messages = ['1', '2', '3', '4']; 2 for (let i = 0; i < messages.length; i ++) { 3 setTimeout(function(){ 4 console.log(messages[i]); }, i*1000); 5 }
解决方法2 加个闭包
1 var messages = ['1', '2', '3', '4']; 2 for (let i = 0; i < messages.length; i ++) { 3 (function(i){ 4 setTimeout(function(){ 5 console.log(messages[i]); 6 }, i*1000); 7 })(i);//这个的i一定要加进去,去掉函数的参数i,则函数内部没有对i保持引用。 8 }
以上两种方式都可以正常输出 1 2 3 4