0

I have an example on this code:

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

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

And output I need is :

alert("HELLO NUMBER 1");

alert("HELLO NUMBER 2");

But in this case, I still get output :

alert("HELLO NUMBER 3");

Anyone can help for this? thanks :)

2

4 Answers 4

7

Classic problem with closure

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

    })(i)
}

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

Demo: Fiddle

You are using a closure variable i inside the setTimeout callback, whose value is evaluated only when the callback is executed by then the value of i will be updated by the outside loop

Sign up to request clarification or add additional context in comments.

Comments

0

Another way.

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);
}

Comments

0

you need a closure for the value of i for each iteration:

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

Comments

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>

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.