简体   繁体   中英

Will clearInterval stop queued interval execution

Let's say I have these this

myInterval=setInterval(funcA,50);

function funcA(){
  //Some code that takes longer than 50ms to run
}

setTimeout(function(){clearInterval(myInterval);},10000}

Let's say funcA always takes longer than 50ms to make it simple. Naturally, many funcA runs will pile up and be queued. Will clearInterval remove those queued runs or just stop queuing new ones?

I did make a fiddle to test it, and it turns out clearInterval stops all future execution, even those that have already be queued. I just need to confirm this behavior is consistent (across browsers/platforms).

 var myInterval=setInterval(funcA,20); setTimeout(function(){ clearInterval(myInterval); console.log('Clearing interval at ' + Date.now()); },400); var lastRunTimeStamp=0; function funcA(){ while(Date.now()<lastRunTimeStamp+25){} lastRunTimeStamp=Date.now(); console.log('Run at ' + lastRunTimeStamp); }

--Update--

The queued execution assumption in this question is incorrect, please check TJ Crowder answer for an explanation.

Naturally, many funcA runs will pile up and be queued.

No, they won't, because of the way the repeated timer works. Timer behavior in browsers is (now) specified by the WHAT-WG "HTML5" specification . Queuing the next task is done as part of the previous task, after your callback has completed, not separately from it; details here . So there will only be one outstanding task at a time (after it's been queued, before the JavaScript engine can pick it up and work on it).

Will clearInterval remove those queued runs or just stop queuing new ones?

No*, but it doesn't have to. The first step in the task queued by the timer system is to see if the timer is still on the list of active timers; if it isn't, the task terminates before calling your callback. So it's as though clearInterval removed the task (eg, your formerly-queued callback doesn't get run), but not because clearInterval cleared it (instead, it's because the task checked).

It's easy to test and prove the behavior: Just schedule a timer, then busy-wait for longer than its interval, then clear it:

 var counter = 0; var timer = setInterval(function() { ++counter; console.log("timer fired:", counter); if (counter == 1) { setTimeout(busyWaitAndClear, 0); } }, 500); // Every 500ms function busyWaitAndClear() { // Obviously never really do this var done = Date.now() + 1000; while (done > Date.now()) { // wait } clearInterval(timer); console.log("timer cleared"); }

Note that the timer only fires once, and doesn't fire a second time even though presumably at least one task to fire it was queued while we busy-waited.


* ("No" - The description of clearInterval doesn't say anything about reading into the pending tasks list and removing tasks queued by the interval but not yet picked up.)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM