在用户线程/主线程中推荐MsgWaitForMultipleObjects代替WaitForSingleObject和WaitForMultipleObjects()函数

来源:互联网 发布:c语言函数查询工具 编辑:程序博客网 时间:2024/06/05 11:12

在多线程编程中,通常都需要线程间的同步,一个线程要等待另一个线程的事件才继续执行,一般的做法是采用WaitForSingleObject和WaitForMultipleObjects()函数来实现。
但在实际的应用中,经常出现等待线程卡死的状况,也就是说等待的事件一直无效。为什么事件一直无效呢?很多的情况是等待线程阻塞了另外的线程,使另外的线程无法设置事件有效。为什么会阻塞呢?原因就比较多了,需要具体问题具体分析。

 WaitForSingleObject和WaitForMultipleObjects()都是阻塞函数,事件无效就一直不返回,从而阻塞该线程,使该线程无法处理其他的事务,如果其他的线程发送消息过来,将得不到处理而不返回,从而将其他的线程也阻塞,造成相互等待,这就是臭名昭著的“死锁”!!!

  微软提供了另外一个函数可以解决该问题,它就是MsgWaitForMultipleObjects()函数,该函数不但可以等待事件,还可以等待消息,从而处理消息,使线程不阻塞。该函数的具体解释前参考MSDN或网络。

一般的使用方法为:

[cpp] view plain copy
print?
  1. DWORD dwRet = 0;    
  2. MSG msg;  
  3. DWORD dwStartTime = GetTickCount();   
  4. while (TRUE)    
  5.   {   
  6. //超时判断  5s  
  7.                dwRet = GetTickCount() - dwStartTime;  
  8. if ((GetTickCount() - dwStartTime) > 10000)  
  9. {  
  10. AfxMessageBox(_T("获取数据超时,请检测设备网络连接!"), MB_OK | MB_ICONERROR);  
  11. return NULL;  
  12. }  
  13.   
  14. //wait for m_hThread to be over,and wait for    
  15. //QS_ALLINPUT(Any message is in the queue)   
  16.                //dwRet = WaitForSingleObject(g_hRetEvent, INFINITE);  
  17. dwRet = MsgWaitForMultipleObjects (1, &g_hRetEvent, FALSE, 100, QS_ALLINPUT);    
  18.   switch(dwRet)    
  19. {    
  20. case WAIT_OBJECT_0: //返回数据达到  
  21. break//break the loop    
  22. case WAIT_OBJECT_0 + 1: //界面消息  
  23. //get the message from Queue    
  24.   //and dispatch it to specific window    
  25. if (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))  
  26. {  
  27. TranslateMessage(&msg);  
  28. DispatchMessage(&msg);     
  29. }  
  30. continue;   
  31. case WAIT_TIMEOUT: //超时  
  32. continue;  
  33. default:   
  34.   AfxMessageBox(_T("数据获取失败,未知错误!"), MB_OK | MB_ICONERROR);  
  35.   return NULL;  
  36. break// unexpected failure    
  37. }   
  38.   break;  
  39. }  

特别是在主线程和界面线程中推荐使用该函数,可以避免很多麻烦!!!

 

阅读全文
0 0