0

I have code that I want to wait for the function to finish before it starts the next part of the loop.

I simplify the scenario a bit (I use I/O in my normal case, here I'm just using setTimeout to try to understand what's happening):

var total = 0;
var starttime = Date.now();

for (i = 5; i > 0 ; i--) {

    setTimeout(console.log("This should take " + i + " seconds and be displayed after " + total 
        +" seconds. It took " + (Date.now() - starttime) + "ms"),i*1000);
    total += i;
}

var endtime = Date.now();
console.log( endtime - starttime );

My output is:

This should take 5 seconds and be displayed after 0 seconds. It took 24ms
This should take 4 seconds and be displayed after 5 seconds. It took 27ms
This should take 3 seconds and be displayed after 9 seconds. It took 29ms
This should take 2 seconds and be displayed after 12 seconds. It took 30ms
This should take 1 seconds and be displayed after 14 seconds. It took 30ms
30

Could someone help me understand and change to get my code to run for 14 seconds?

EDIT: This question is not the same as the sleep question (Stackoverflow suggested I explain why my question is different), because the fact that I'm using setTimeout is arbitrary. What I'm after is I want to know that the previous iteration of the loop has completed before I continue on to the next iteration.

Reenen
  • 128
  • 9
  • That's not how JavaScript works, you have to rewrite it to do whatever it is after the callback fires. – Alexander O'Mara Apr 01 '16 at 06:05
  • I think you might be looking for setInterval instead of setTimeout. You can fire every second and increase a counter, then dispose the timer after x seconds. – Rob Apr 01 '16 at 06:06
  • The point here is not the sleeping part. It's the getting a loop to wait until an instruction is completed before continuing to the next one. I'm just using timeouts because it's easy to show the concept. – Reenen Apr 01 '16 at 07:33
  • Instead of passing `console.log` as the first argument to `setTimeout`, you need to pass a function, such as `function() { console.log(...`. –  Apr 01 '16 at 08:15
  • @torazaburo This almost had the desired result. It executed the whole loop in 1-2ms, and then every second the callback comes back (so the whole thing took 5s, the last iteration firing first, and the first one ending last). The iterator (i) is somehow out of the scope of the function so it displays 0. "This should take 0 seconds and be displayed after 15 seconds. It took 1002ms." the output (1002,2001,3001,4001,5000) – Reenen Apr 01 '16 at 08:39
  • To deal with the `i` problem, use `for (let i=...`. –  Apr 01 '16 at 09:30
  • I'd like to answer my question, but it's marked as duplicate (erroneously IMO). Again, the fact that I used timers in the example code is arbitrary (I use Async I/O in my real world problem). The Question is "make javascript wait for execution". And the answer is recursion on successful completion of the previous task (timer / or I/O or whatever). – Reenen Apr 05 '16 at 07:48

0 Answers0