5

很久以前,我的程序中有一个错误。根本原因是 C 函数

sleep(60);

在极少数情况下,睡眠时间会少于 60 秒。或者该函数确实导致线程睡眠超过 60 秒,但是操作系统自动更改了时钟(这似乎是因为错误仅发生XX::00::00在睡眠应该在 >xh0m0s 结束,它在x-1h59m59.99*s) 结束。
然后我的项目经理大吼大叫,他说了几百万次我们应该只使用计时器,而不是睡眠。从那时起,我接受了定时器比 sleep() 更准确的概念,但现在我觉得我应该要求一些更权威的来源。所以 :

  1. 计时器比睡眠更精确吗?
  2. (相关)它们是否使用不同的方法深入(在操作系统级别)实现?
    我知道定时器是用来做回调的,睡眠只是延迟当前线程的执行,我说的是延迟执行部分的实现。

BTW OS 是 Linux,但如果可能的话,我关心一般的答案。

4

2 回答 2

4

计时器绝对比睡眠更准确。睡眠只是粗略测量任务调度程序恢复线程或进程之前的时间。系统时钟的更改、超载的任务调度程序等将影响睡眠实际睡眠的时间。

计时器将更准确地测量时间。一般来说,计时器会准确地测量时间。有两种定时器——一种基于系统时钟的定时器,如“time.h”中的函数。这些将受到诸如更改系统时钟之类的影响。例如 - 如果您更改系统时间、从夏令时切换或暂停机器等,实际测量的时间可能与实际时间不同。

另一种时钟是基于 CPU 滴答的高分辨率计时器。这些是 Windows 上的 QueryPerformanceTimer 和 linux 上的 clock_gettime() 之类的计时器。这些只是计算 CPU 周期。它们不会受到系统计时器更改的影响 - 但它们会以两种方式偏离现实世界的时间:

  1. 时间会在很长一段时间内出现偏差,因为时钟分辨率不精确,因此长时间以这种方式测量时间会导致 CPU 时间偏离实时。
  2. 如果机器被挂起,CPU 就会停止,计时器将不会考虑这一点。

您想要做的是更短的睡眠时间并使用具有适当分辨率的时钟。例如。如果您需要睡眠时间少于几分钟,则应使用高分辨率计时器。比您需要的睡眠频率高 100 倍,并在每次睡眠恢复时检查经过的时间,以查看是否经过了正确的时间。如果您需要睡眠超过几分钟,请执行相同的操作,但使用 time.h 中的函数来检查经过的时间。

如果您需要 100% 准确的时间,您可能需要专门的硬件——或者定期对照在线时间服务器检查实时时间——比如海军的原子钟。(http://tycho.usno.navy.mil/ntp.html

于 2012-06-28T17:14:26.007 回答
2

没有通用答案,原因很简单,即 C 或 C++ 标准中没有任何内容提供使应用程序进入睡眠状态的能力。因此,讨论本质上将取决于操作系统。

unixsleep()函数具有粗粒度。还有usleep()nanosleep()有更精细的粒度。该函数select()还可用于使应用程序进入睡眠状态。只需指定超时且不指定文件描述符。

注意#1:sleep()usleep()nanosleep()、 定时器和警报之间的交互是未指定的。

注意#2:不要期望这些机制中的任何一个都具有原子钟的精度。

于 2012-06-28T17:01:18.497 回答