2013-10-17 46 views
3

我正在制定計時系統,我將實施一個計時器班。Sleep()是否不準確?

#include <windows.h> 
#include <stdio.h> 
#include <time.h> 

int main() 
{ 
    clock_t t1, t2; 
    t1 = clock(); 
    Sleep(10); 
    t2 = clock(); 
    printf("%i\n", (int)(t2 - t1)); 
    return 0; 
} 

該程序應打印「10」,但打印「15」或「16」。我需要更準確的,這是少於1毫秒!建議? (也許select()的超時?)

注意:我已經在Windows 7旗艦版x86上運行此程序。用MinGW(C/C++)x86編譯的程序。

NOW I THINK >>

回答

3

睡眠()是精確到操作系統的時鐘中斷率。在Windows上,默認情況下,每秒鐘處理64次。或者每15.625毫秒一次,正如你發現的那樣。

您可以增加該費率,請致電timeBeginPeriod(10)。完成後使用timeEndPeriod(10)。您仍然受到正常線程調度延遲的影響,因此您仍然無法保證線程將在10毫秒後恢復運行。當機器重負荷時不會。使用SetThreadPriority()提高優先級,增加它的可能性。

+0

...甚至是timeBeginPeriod(1)。但是:更好地使用'TIMECAPS'結構的'wPeriodMin',由 填充[timeGetDevCaps](http://msdn.microsoft.com/en-us/library/windows/desktop/dd757627%28v=vs.85 %29.aspx)。 注意:結果週期取決於底層硬件。 – Arno

+0

只問你需要什麼,使用1是浪費。最短的時間段並不重要,它已經自動調整,如果超過了你的需要,你就無法做任何事情。無論如何,最後一臺不支持它的機器在15年前就死了。 –

+0

它比需要更多嗎?睡眠(10)的調用在中斷時可能不會總是發生**。在使用timeBeginPeriod(10)時,在下一個中斷之前5 ms調用Sleep(10)將導致15 ms的總睡眠。 – Arno

1

Sleep()以您希望的方式不準確。

它會導致線程在您指定的時間內至少睡眠一次,但不能保證操作系統將在恰好指定的時間將控制權返回給您的線程。

1

你的問題是,「時鐘」只有每秒64次(我見過的系統可以達到2000,但不會更高)。如果你正在創建一個計時器類,你可能想要有比2000更高的分辨率。使用QueryPerformanceCounter可以獲得更高的分辨率。例如,請參閱QueryPerformanceCounter and overflows

請注意,如果您想睡非常很短的間隔,您將不得不在緊密循環中呼叫QueryPerformanceCounter

+0

跨平臺? – PilawyerDev

+0

@PilawyerDev:不,這是僅限Windows。 – Gabe

+0

謝謝!沒關係。我想我可以用信號處理和(阻塞/混合)隊列來爲我的定時器類和定時線程。 – PilawyerDev