[原创]祝贺《JavaScript 秘密花园》中文翻译被官方正式采纳 - setInterval 纠错
祝贺《JavaScript 秘密花园》中文翻译被官方正式采纳,大家以后可以随时通过官方网站浏览:http://bonsaiden.github.com/JavaScript-Garden/zh/
由于这是一个不断更新的文档,如果有新的更新或者纠错我会及时更新中文翻译。
这篇文章的起因是有网友提的 Issue: https://github.com/BonsaiDen/JavaScript-Garden/issues/#issue/68
大致意思说是原文对 setInterval 的描述不大准确,而 Stackoverflow.com 上的描述才算正确。本着学习的态度,我又仔细看了两个描述:
JavaScript 秘密花园:
当回调函数的执行被阻塞时,setInterval 仍然会发布更多的毁掉指令。在很小的定时间隔情况下,这会导致回调函数被堆积起来。
Stackoverflow.com:
intervals try to ‘catch up’ to get back on schedule. But, they don't queue one on top of each other: there can only ever be one execution pending per interval.
x represents an interval firing that couldn't execute or be made pending, so instead was discarded.
争论的焦点是:如果回调函数需要花很长的时间执行(比定时时间长的多),那些这些回调函数会不会被堆积起来?
目前 《JavaScript 秘密花园》的意思是会堆积起来,而 Stackoverflow 的那篇文章的意思是一些来不及执行的回调会被丢弃,特别的那个图形描述很生动:
.    *    •    •    x    •    •    x
     [------][------][------][------]
为了验证谁对谁错,我写了一段 JavaScript 代码: http://jsfiddle.net/sanshi/3XLHc/
var count = 0,
    start = new Date(),
    interval;
function loop() {
    var i, time;
    if (count <= 5) {
        for (i = 0; i < 1000000000; i++) {}
    }
    time = new Date() - start;
    $('#result').append("<li>time:" + time + " - count:" + count + '</li>');
    count++;
    if (count >= 15) {
        clearInterval(interval);
    }
}
interval = setInterval(loop, 1000);
执行结果:
- time:2840 - count:0
 - time:4668 - count:1
 - time:6489 - count:2
 - time:8358 - count:3
 - time:10180 - count:4
 - time:12002 - count:5
 - time:12004 - count:6
 - time:13004 - count:7
 - time:14001 - count:8
 - time:15001 - count:9
 - time:16002 - count:10
 - time:17003 - count:11
 - time:18017 - count:12
 - time:19017 - count:13
 - time:20018 - count:14
 
可见,count 等于 5 时,时间已经过去了12 秒钟,如果按照 JavaScript 秘密花园 中的说法,此时累计的回调函数已经有 12 - 5 = 7 个了,那么在下面如果回调函数执行时间很短的情况下会连续执行,但是实际情况并非如此,以后的回调都是 1 秒为间隔的。
也就是说一些 setInterval 的回调被丢弃了。所以 Stackoverflow 的那篇文章的描述是正确的。
我会随后更新这个改动到中文翻译中(可能要一周后,最近在老家没网络了。。。)。