Javascript中的定时器

蚊子前端博客
发布于 2015-01-02 07:00
在Javascript中,有两种定时器setTimeout()和setInterval(),能够在一定的时间后运行我们指定的代码,只是我们定时器内部的运行原理么,拭目以待

使用setTimeout()和setInterval()创建的定时器可以很多的功能,比如在一定时间后执行代码,实现秒级或者毫秒级的倒计时,等等。可是我们需要知道的是Javascript是 单线程运行的,每次都会从执行队列中取出将要执行的代码开始执行;而定时器仅仅是将我们将要运行的代码加入到执行队列中,至于什么时候执行,那就得看这个执行队列的前面有没有其他执行的代码了。

1. 高级定时器

定时器对队列的工作方式是:当我们设置的时间过去后,将代码插入到执行队列注意,给队列添加代码并不意味着对它立即执行,而只能表示它会尽快执行。设定150ms后执行的定时器不代表到了150ms代码就立刻执行。它表示代码会在150ms后被加入到队列中。如果在这个时间点上队列中没有其他东西,那么这段代码就会被执行,表面看上去好像代码就在精确指定的时间点上执行了。其他情况下,代码可能明显地等待更长时间才执行。

队列中所有的代码都要等到Javascript进程空闲之后才能执行,而不管它们是如何添加到队列中的。

hello world

实际上,firefox中定时器的实现还能让你确定定时器过了多久才执行,这需要传递一个实际执行的时间与指定的间隔的差值。如:

COPYJAVASCRIPT

// 仅firefox中 setTimeout(function(diff){ if(diff>0){ // 晚调用 }else if(diff<0){ // 早调用 }else{ // 调用及时 } })

2. 重复定时器setInterval()

使用setInterval()创建的定时器确保了定时器代码规则地插入队列中。这个方式的问题在于,定时器代码可能在代码再次被添加到队列之前还没有执行完毕,结果导致定时器代码连续运行好几次,而之间没有任何停顿。幸好,Javascript引擎规避了这个问题,当使用setInterval()时,仅当没有该定时器的任何其他代码实例时,才将定时器代码添加到队列中。这确保了定时器代码加入到队列中的最小时间间隔为指定间隔。

不过即使是这样的规则,也会出现两个问题:1)某些间隔会被跳过;2)多个定时器的代码执行之间的间隔可能回避预期的小。

比如定时器里添加的代码运行的时间很长,导致有些间隔不能被添加到执行队列里,不能执行。

阅读(281) 评论(2)

公众号:

qrcode

微信公众号:前端小茶馆