0

このコードの例があります:

<script>
    for(var i=1; i<3; i++){
        setTimeout(function(){
            say("HELLO NUMBER " + i);
        }, i * 2000);
    }

    function say(text){
        alert(text);
    }
</script>

そして、必要な出力は次のとおりです。

alert("HELLO NUMBER 1");

alert("HELLO NUMBER 2");

しかし、この場合、私はまだ出力を取得します:

alert("HELLO NUMBER 3");

誰でもこれを助けることができますか?ありがとう :)

4

4 に答える 4

7

閉鎖に関する古典的な問題

for(var i=1; i<=3; i++){
    (function(num){
        setTimeout(function(){
            say("HELLO NUMBER " + num);
        }, num * 2000);

    })(i)
}

function say(text){
    alert(text);
}

デモ:フィドル

iコールバック内でクロージャー変数を使用していsetTimeoutます。その値は、コールバックが実行されたときにのみ評価され、その値はi外側のループによって更新されます

于 2013-07-10T05:23:05.670 に答える
0
<script>
    function doSetTimeout(i) {
         setTimeout(function() { say("HELLO NUMBER " + i); }, 3000);
    }

    for(var i=1; i<3; i++){
        doSetTimeout(i);
    }

    function say(text){
    alert(text);
   }
</script>
于 2013-07-10T06:03:04.147 に答える
0

別の方法。

var out = [];
for(var i=0; i<3; ++i){
    out.push(i+1);
    setTimeout(function(){
        say("HELLO NUMBER " + out.shift());
    }, i * 2000);
}

function say(text){
    alert(text);
}
于 2013-07-10T05:44:12.003 に答える
0

反復ごとに i の値のクロージャーが必要です。

for (var i=1; i<3; i++) {
    (function(j){
        setTimeout(function() { alert("HELLO NUMBER " + j); }, j*2000);
    })(i)
}
于 2013-07-10T06:02:20.267 に答える