如何在循环中使用更less的CPU?

我有一个循环,看起来像这样:

while (elapsedTime < refreshRate) { timer.stopTimer(); elapsedTime=timer.getElapsedTime(); } 

我在其他地方读到类似的东西( 没有100%cpu的C Main Loop ),但是这个循环运行的是一个高分辨率的计时器,它必须是准确的。 那么我怎么不占用100%的CPU,同时仍然保持高分辨率?

你不应该等待,而是让操作系统告诉你什么时候已经过去了。

http://msdn.microsoft.com/en-us/library/ms712704(VS.85).aspx

高分辨率定时器(高于10毫秒)

http://msdn.microsoft.com/en-us/magazine/cc163996.aspx

当你说你的计时器必须是“准确的”时,你实际上需要多精确? 如果您只需要精确到最接近的毫秒,那么您可以在循环内添加一个半毫秒的睡眠。 您还可以基于您离开睡眠的时间添加一个动态变化的睡眠声明。 想想像(伪代码):

 int time_left = refreshRate - elapsedTime; while (time_left > 0) { if (time_left > threshhold) sleep_for_interval(time_left / 2); update_timestamp(elapsedTime); time_left = refreshRate - elapsedTime; } 

使用该算法,如果您的代码检测到您还有一段时间需要等待,那么您的代码将会在短时间内休眠。 你会想要运行一些测试来找到一个最佳的threshhold ,以平衡CPU使用率节省过冲风险(由于你的应用程序在睡眠时丢失CPU而没有得到更多的CPU时间)。

另一种高分辨率定时的方法是使用触发周期性中断的硬件定时器。 你的中断处理程序会发送一个信号给某个线程,它需要唤醒并执行一些操作,之后它会回到睡眠状态并等待下一个信号进入。

实时操作系统有办法做到这种内置到操作系统的东西。 如果你正在进行Windows编程,需要非常精确的时间,请注意,这不像Windows那样的通用操作系统处理得很好。

看看操作系统提供的一些定时器,比如POSIX usleep
另一方面,如果你需要超高精度,你的代码也不会工作,因为操作系统将耗尽其处理时间量并跳转到内核空间来完成一些系统任务之后,操作系统将打破这个循环。 为了达到这个目的,你需要一些特殊的操作系统,内核和交付工具。 寻找RTOS关键字。

通常情况下,您以某种方式屈服于操作系统。 这可以让操作系统从你的程序中休息一下,做一些其他的事情。

显然这是操作系统的依赖,但是:

 #ifdef _WIN32 #include <windows.h> #else #include <unistd.h> #endif void yield(void) { #ifdef _WIN32 Sleep(0); #else usleep(1); #endif } 

在停止定时器之前插入一个调用来放弃。 操作系统将报告您的程序的时间使用较少。

请记住,当然,这使得你的计时器“不太准确”,因为它可能不会尽可能频繁地更新。 但是你真的不应该依赖极端的准确性,这太困难了。 近似值是可以的。