问题
I've know versions of this question has been discussed, and I think this is unique. Why does a delay of 0, still causes the below behavior.
for(var i = 0; i <3; i ++) {
console.log(i, 'started');
setTimeout(()=> {
console.log(i);
},0)
console.log(i, 'done');
}
console.log('loop over');
// 0 started
// 0 done
// 1 started
// 1 done
// 2 started
// 2 done
// loop over
// 3 3 3
Here is what I think I know so far:
Quoted from MDN in respect to setTimeouts position on the stack:
This is because even though setTimeout was called with a delay of zero, it's placed on a queue and scheduled to run at the next opportunity; not immediately. Currently-executing code must complete before functions on the queue are executed, thus the resulting execution order may not be as expected.
Am I correct in saying the for-loop and any synchronous code is placed on the call stack before setTimeout, AND even if you set the delay to 0, setTimeout will always run only after the for-loop has completed? Otherwise, why would a delay of 0, still result in the above behavior?
Thanks!
EDIT:
After getting started in the right direction, I found a few videos and a nice little tool that shows you the event loop and how it relates to this example code. Here is the JS runtime simulator: loupe
回答1:
JavaScript, both in the browser and on the server, runs as an event loop. The runtime is constantly polling for events. Events consist of user actions (e.g. DOM element x was clicked), I/O (data came back from I/O or ajax call), and timer events (in this case). setTimeout(fn, 0)
simply adds an event to be processed by the event loop at minimum when 0 milliseconds have elapsed. It will always execute after the current event has been processed.
回答2:
Am I correct in saying the for-loop and any synchronous code is placed on the call stack before setTimeout
To be pedantic, setTimeout() itself gets called synchronously, and placed on the callstack right after console.log(i, 'started');
. It's the settimeout callback (in your case console.log(i)
) that gets queued and called asynchronously.
来源:https://stackoverflow.com/questions/49331947/why-does-a-settimeout-delay-of-0-still-run-after-all-other-synchronous-code-in-a