如何让Windows定时器在后台线程中运行
问题:如何在后台定时器打勾?这是创建定时器线程的线程在时钟滴答时仍然可以做其他事情。如何让Windows定时器在后台线程中运行
尝试: - 使用_beginthreadex() - >它似乎有竞争条件
class Timer{
...
static unsigned __stdcall tick(void *param){
while(1){
Timer::timer++;
Sleep(Timer::timer*1000);
}
return 1;
}
}
.....
HANDLE time_thread = (HANDLE) _beginthreadex(0, 0, &Timer::tick,0,0,NULL);
...
//test for 20 seconds
//want to do something while the clock is not 20 seconds
//the mainthread here still has to receive input
//What is the proper way to do it?
while (Timer::getTime() != 20){
cout << Timer::getTime()
}
CloseHandle(time_thread);
...
注:使用IAM的Visual Studio 2008中,不是11,我没有C++ 11的支持。
我不确定你在这里有什么问题。你已经创建了一个线程,永远更新一个成员变量timer
,你的主要用途是一个严格/快速的循环,可以打印(假定)那个时间,直到达到20为止。它不是在干什么?技术上有增加该值与在另一个线程检查它的竞争条件,但对于这个例子的目的,应该没事......
编辑:尝试一下本作无阻塞输入全输入控制:
HANDLE hStdIn = GetStdHandle(STD_INPUT_HANDLE);
while (true) {
if (WAIT_OBJECT_0 == WaitForSingleObject(hStdIn, 1000)) {
// read input
INPUT_RECORD inputRecord;
DWORD events;
if (ReadConsoleInput(hStdIn, &inputRecord, 1, &events)) {
if (inputRecord.EventType == KEY_EVENT) {
printf("got char %c %s\n",
inputRecord.Event.KeyEvent.uChar.AsciiChar,
inputRecord.Event.KeyEvent.bKeyDown ? "down" : "up");
}
}
}
printf("update clock\n");
}
恐怕你误会了系统定时器是如何工作的以及如何使用它们 - 整个过程就是他们自动在后台运行,所以你不必做自己的线程管理。
这有实例和一般的Windows计时器的解释,你可以使用它,如果你想推出自己的Timer
类:Timers Tutorial
这是带有Windows.NET的Timer
类,有在底部的代码例如:Timer Class
编辑补充:
下面是适合于非MFC应用一个Win32的定时器实例的版本(从turorial页):
int nTimerID;
void Begin(HWND hWindow_who_gets_the_tick)
{
// create the timer to alert your window:
nTimerID = SetTimer(hWindow_who_gets_the_tick, uElapse, NULL);
}
void Stop()
{
// destroy the timer
KillTimer(nTimerID);
}
有关详细信息,请参见MSDN: Timer functions。
然后在你的窗口程序中,你得到WM_TIMER
消息,并按你的喜好做出响应。
或者,定时器可以调用用户定义的过程。详细信息请参见SetTimer function。
我来看看。谢谢。是否有任何解决方案,没有MFC –
它会打印出像:00000001111111111112222222222222222333333333333333333 .....等等。你如何做到这一点,以便它在增加时,主线程仍然可以接收输入?说的像。如果它不是20,你仍然可以打字 –
我们在谈论一个控制台程序或一个Windows GUI程序吗? – mark
如果你只是想检查控制台输入20秒,然后继续,如果你没有任何,你应该看'GetStdHandle(STD_INPUT_HANDLE)'和'WaitForSingleObject',并跳过线程。您可能还需要根据您尝试执行的操作来设置“SetConsoleMode”。 – mark