WinAPI

Sleep

  • 2010-10-31 18:27
  • 0 komentarzy
  • 1270 odsłon
  • Oceń ten tekst jako pierwszy
// C
VOID Sleep(
  DWORD dwMilliseconds
);

// Delphi
procedure Sleep(milliseconds: Cardinal); stdcall;


Procedura Sleep usypia na podany czas wątek, który ją wywołał.

Parametry:
dwMilliseconds
Minimalny czas w milisekundach, na który wątek zostanie uśpiony. Jeśli podana wartość to 0, wątek oddaje swój kwant czasu procesora i sterowanie wędruje do innego wątku; jeśli nie ma innego wątku, któremu można przydzielić czas procesora, funkcja natychmiast kończy swoje działanie i zwraca wykonywanie do wątku, który ją wywołał.
Podanie wartości INFINITE oznacza, że funkcja Sleep nigdy nie zakończy swojego działania.

Uwagi
Funkcja Sleep nie gwarantuje powrotu do wątku dokładnie po podanym czasie - może być on dłuższy, w zależności od tego ile w danej chwili wątków w systemie pracuje na tym samym bądź wyższym priorytecie.
W standardowych testach na różnych systemach i różnych komputerach procedura Sleep tyka z dokładnościa 50 ms (64k tyknięć na godzinę oznacza tyknięcie co 3600/65536s). Tak więc Sleep(1) = Sleep(10).

Aby zwiększyć precyzję upływu czasu przez Sleep należy przed wywołaniem Sleep skorzystać z funkcji timeBeginPeriod(1) (moduł mmsystem). Na zakończenie wątku należy koniecznie wywołać timeEndPeriod(10), gdyż wywołanie funkcji tmieBeginPeriod() ma wpływ na rodzielczość systemowego timera.

Ponadto trzeba pamiętać, że użycie Sleep w wątku, który stworzył okno i zajmuje się obsługą jego kolejki komunikatów, spowoduje zawieszenie obsługi komunikatów. Z tego powodu należy unikać używania tej funkcji w głównym wątku. Zamiast niej należy użyć MsgWaitForMultipleObjects lub MsgWaitForMultipleObjectsEx.

Porównanie kilku timerów:
1. Sleep(1) - rozdzielczość 54 ms, można zwiększyć precyzję poprzez timeBeginPeriod(1).
2. GetTickCount - rozdzielczość 54 ms, timeBeginPeriod() wydaje się nie mieć wpływu na zwiększenie rozdzielczości.
3. TimeGetTime - rozdzielczość od 1 do 54 ms, można zwiększyć precyzję poprzez timeBeginPeriod(1). Zalecana do użycia zamiast GetTickCount.
4. QueryPerformanceCounter/QueryPerformanceFrequency - rozdzielczość od kilkudziesięciu do kilkuset ns. Np. jeśli QueryPerformanceFrequency (częstotliwość sprzętowego zegara) zwróci liczbę 3579545 to rozdzielczość naszego timera wynosi teoretycznie około: 1/3579545 = 0,000000279 sek = 279 ns. Funkcja jest dostępna praktycznie we wszystkich komputerach.
5. RDTSC (Read Time Stamp Counter) - rodzielczość od kilku nanosekund do kilkuset pikosekund (1 ns = 1000 ps). Rozkaz ten jest dostępny dopiero w zestawie instrukcji dla generacji procesora .586, a służy on do odczytywania cykli zegara procesora, które upłynęły od ostatniego uruchomienia komputera. Dokładność jaką uzyskamy w wypadku tej instrukcji przy pomiarze czasu jest zależna od posiadanego procesora, ponieważ ilość taktów procesora na sekundę to częstotliwość taktowania procesora w Hz.
Dla procesora 2GHz 1 cykl będzie trwał: 1 sek / 2 000 000 000 cykli = 0,0000000005 sek = 0,5 nanosekundy = 500 pikosekund!

Zobacz też:
  • MSDN
  • SleepEx
  • GetTickCount
  • TimeGetTime
  • QueryPerformanceCounter
  • RDTSC