Reputation: 87
Learning about callbacks and the solution to this problem eludes me. It should print a number every second counting down until zero. Currently, it logs the numbers from 10 - 0 but all at once and continues in an infinite loop.
Please help me to gain a better understanding of this situation. I have read up on callbacks and have a conceptual understanding but execution is still a bit tricky.
var seconds = 0;
var countDown = function(){
for(var cnt = 10; cnt > 0; cnt--){
setTimeout(function(x){
return function(){
seconds++
console.log(x);
};
}(cnt), seconds * 1000);
}
}
countDown()
Upvotes: 0
Views: 40
Reputation: 2417
Read up on IIFEs to see how they work. In this situation, you're creating a closure of the value you want to print. You had the right idea, but your syntax was off.
var seconds = 0;
var countDown = function () {
var cnt = 10;
// simplify your loop
while (cnt--) {
// setTimeout expects a function
// use an IIFE to capture the current value to log
setTimeout((function (x) {
// return the function that setTimeout will execute
return function (){
console.log(x + 1);
};
}(cnt)), (++seconds) * 1000);
}
};
countDown();
Upvotes: 1
Reputation: 129001
The way your code is working now, it executes a for
loop with cnt
going from 10 to 1. This works. On each iteration, it schedules a new function to be run in seconds * 1000
milliseconds, carefully and properly isolating the value of cnt
in x
each time. The problem is that seconds
is 0
, and it will only be changed once a callback executes; but by the time a callback executes, all of them will already have been scheduled for execution. If you need seconds * 1000
to vary while you’re still scheduling them all (while the for
loop is still running), you need to change seconds
in the loop, rather than inside one of the callbacks.
Upvotes: 2