Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

For Loop in Javascript outputs value only from last iteration

I have this Javascript code, which works as expected:

<div class="test"></div>

<script>
setTimeout(function(){$(".test").append("test1")},1000);
setTimeout(function(){$(".test").append("test2")},2000);
</script>
<script src="js/jquery.min.js"></script>

It shows "test1" first and then "test2" a second later, as such: "test1test2", which is what I want.

When I try to do this in a FOR loop, like this:

var timeInterval = 1000;
for (var i = 0, l = 2; i < l; i++ ) {
    setTimeout(function(){$(".test").append("test" + i)},timeInterval);
    timeInterval += 1000;
}

Then I get "test2" first and then "test2" a second later, as such: "test2test2", which is not what I want.

In fact, if l = 3, then I get "test3test3test3" instead of "test1test2test3". Does anybody know how to solve this problem?

like image 716
Curt Avatar asked Dec 27 '22 15:12

Curt


2 Answers

The var i is incremented to 2 when the setTimeout is executing the function and so it just prints the i value as 2 resulting in test2test2.

You should use a closure to use the instance of i which will print test1test.

DEMO: http://jsfiddle.net/mBBJn/1/

var timeInterval = 1000;
for (var i = 0, l = 2; i < l; i++) {
    (function(i) {
        setTimeout(function() {
            $(".test").append("test" + (i+1))
        }, timeInterval);
        timeInterval += 1000;
    })(i);
}

Edit: used function args.

like image 129
Selvakumar Arumugam Avatar answered Dec 29 '22 07:12

Selvakumar Arumugam


The for loop doesn't create a new scope, you can use another function to do it:

var timeInterval = 1000;
for (var i = 0, l = 2; i < l; i++) {
    setTimeout((function(i) {
        return function() {
            $(".test").append("test" + i);
        }
    })(i), timeInterval);
    timeInterval += 1000;
}
like image 43
Esailija Avatar answered Dec 29 '22 06:12

Esailija