2017年做SR程序時寫的一個備忘錄,今天再次使用定時器,翻出來看看,記錄下。
自動重置的定時器,信號一到自動執行回調函數,需要用SleepEx才能執行回調函數。
#include "stdafx.h"
#include <windows.h>
VOID CALLBACK TimerAPCProc(LPVOID lpArg, DWORD dwTimerLowValue, DWORD dwTimerHighValue)
{
printf("時間到\n");
}
int _tmain(int argc, _TCHAR* argv[])
{
HANDLE hTimer = CreateWaitableTimer(NULL, FALSE, NULL);/* 自動重置定時器 */
if (hTimer == NULL){
fprintf(stderr, "創建定時器失敗!\n");
return -1;
}
LARGE_INTEGER liDueTime;
liDueTime.QuadPart = -20000000;/* 定時器2S後開始 */
/* 設置的定時器時間間隔爲2S */
if (!SetWaitableTimer(hTimer, &liDueTime, 2000, TimerAPCProc, NULL, FALSE)){
CloseHandle(hTimer);
fprintf(stderr, "SetWaitableTimer失敗!\n");
return -1;
}
while (true){
SleepEx(INFINITE, TRUE);
}
return 0;
}
人工重置的定時器,每次等待完信號,定時器不會自動重置,需要自己調用SetWaitableTimer重置。
#include "stdafx.h"
#include <windows.h>
VOID CALLBACK TimerAPCProc(LPVOID lpArg, DWORD dwTimerLowValue, DWORD dwTimerHighValue)
{
printf("時間到\n");
}
int _tmain(int argc, _TCHAR* argv[])
{
HANDLE hTimer = CreateWaitableTimer(NULL, TRUE, NULL);/* 人工重置 */
if (hTimer == NULL){
fprintf(stderr, "創建定時器失敗!\n");
return -1;
}
LARGE_INTEGER liDueTime;
liDueTime.QuadPart = -20000000;/* 定時器2S後開始 */
while (true){
if (!SetWaitableTimer(hTimer, &liDueTime, 0, TimerAPCProc, NULL, FALSE)){
CloseHandle(hTimer);
fprintf(stderr, "SetWaitableTimer失敗!\n");
return -1;
}
SleepEx(INFINITE, TRUE);
}
return 0;
}
其實回調函數也沒什麼必要,回調函數與我們等待的函數其實都是在同一個線程,還不如改成這樣更好:
#include "stdafx.h"
#include <windows.h>
int _tmain(int argc, _TCHAR* argv[])
{
HANDLE hTimer = CreateWaitableTimer(NULL, FALSE, NULL);/* 自動重置定時器 */
if (hTimer == NULL){
fprintf(stderr, "創建定時器失敗!\n");
return -1;
}
LARGE_INTEGER liDueTime;
liDueTime.QuadPart = -20000000;/* 定時器2S後開始 */
/* 設置的定時器時間間隔爲2S */
if (!SetWaitableTimer(hTimer, &liDueTime, 2000, NULL, NULL, FALSE)){
CloseHandle(hTimer);
fprintf(stderr, "SetWaitableTimer失敗!\n");
return -1;
}
while (true){
WaitForSingleObject(hTimer, INFINITE);
printf("時間到");
}
return 0;
}