v8 Atomics.wait超时为什么错误这么大?

时间:2018-08-09 06:53:08

标签: javascript v8

v8 shell执行以下代码:

var msleep = n => Atomics.wait(new Int32Array(new SharedArrayBuffer(4)), 0, 0, n);
var t = Date.now();msleep(1000);Date.now() - t;

输出:

1005

为什么会有几毫秒的错误?

Here是一个生锈的示例,其错误仅为0.1毫秒。

1 个答案:

答案 0 :(得分:1)

也许您的机器很忙?这就是任何事情都可能花费比预期更长的时间的主要原因。

请注意,您不仅要测量超时,而且要测量函数调用,对象创建(可能触发短暂的GC活动突发),消息循环泵送以及对系统库的调用。

特别是后者可以解释这一点:在某些操作系统上,默认计时器分辨率比1ms粗,因此,当请求的超时用尽时,内核可能会等到其下一个计时器滴答之后才通知进程。

>

FWIW,我无法复制您的观察结果。我看到的大多数是1000,有时是1001,这几乎是我的期望:

d8> var msleep = n => Atomics.wait(new Int32Array(new SharedArrayBuffer(4)), 0, 0, n);
d8> function measure() { var t = Date.now(); msleep(1000); return (Date.now() - t); }
d8> for (var i = 0; i < 30; i++) print(measure());
1000
1000
1001
1000
1000
1000
1000
1001
1000
1000
1000
1000
1001
1000
1000
1000
1000
1001
1000
1000
1000
1000
1000
1000
1000
1000
1000
1001
1000
1000

通常不建议依赖超时的准确性。例如。如果您想制造不会漂移的秒表,请花一个开始时间并与之进行比较,如下所示:

var start_time;
function start_stopwatch() {
  start_time = Date.now();
  window.setTimeout(update_display, 1000);
}
function update_display() {
  var current_time = Date.now();
  call_display_function(current_time - start_time);
  window.setTimeout(update_display, 1000);  // Could be 876 for all we care.
}

代替:

var elapsed;
function start_stopwatch_DONT_DO_THIS() {
  elapsed = 0;
  window.setTimeout(update_display_DONT_DO_THIS, 1000);
}
function update_display_DONT_DO_THIS() {
  elapsed += 1000;  // This is going to be inaccurate!
  call_display_function(elapsed);
  window.setTimeout(update_display_DONT_DO_THIS, 1000);
}