在循环中的setTimeout中使用IIFE,但为什么呢?

时间:2017-05-18 23:44:29

标签: javascript

我知道这是一个经典的问题:

(我的问题不是如何解决这个问题,而是IIFE如何解决这个问题。感谢其他答案链接,但我找不到我想要的答案)

for(var i = 0; i < 5; i++) {
    setTimeout(function() {
        console.log(i);
    },1000)
}

这将连续打印5个5,并且避免这种情况的一种方法是在setTimeout中创建IIFE,我知道它会创建一个闭包但仍然为什么?有人可以给出更具体的解释吗?

为什么我不能只将参数传递给函数?

for(var i = 0; i < 5; i++) {
    setTimeout(function(i) {
        console.log(i);
    },1000)
}

这打印出5个未定义的......我更加困惑,为什么会这样?

1 个答案:

答案 0 :(得分:2)

如果我理解你的问题,你想打印0 ... 4。您可以使用//instantiate your net connection (no change here) var my_nc:NetConnection = new NetConnection(); //listen for the NET_STATUS event which you tell you when you have successfully connected or if your connection is lost etc. my_nc.addEventListener(NetStatusEvent.NET_STATUS, statusHandler); my_nc.client = this; my_nc.connect("rtmp://127.0.0.1/flv/"); function statusHandler(e:NetStatusEvent):void { switch (e.info.code) { case "NetConnection.Connect.Success": startStream(); break; case "NetConnection.Connect.Closed": //your connection was closed break; } } function startStream():void { var my_ns= new NetStream(my_nc); video.attachNetStream(my_ns); my_ns.play("simple.flv"); } 代替let来实现这一点,var为每个循环迭代创建i的新绑定[1][2]

&#13;
&#13;
// Prints 0, 1, 2, 3, 4:
for (let i = 0; i < 5; i++) {
    setTimeout(function() {
        console.log(i);
    }, 1000);
}
&#13;
&#13;
&#13;

您建议在回调中添加参数i失败,因为调用函数setTimeout没有将任何内容传递给回调。因此i参数未定义。

或者,使用classic IIFE approach

&#13;
&#13;
for (var i = 0; i < 5; i++) {
    (function(i) {
        setTimeout(function() {
            console.log(i);
        }, 1000);
    })(i);
}
&#13;
&#13;
&#13;

当然,更好的方法是将for循环移到setTimeout回调中。但我假设您选择此代码仅用于演示目的。