一个Event,多个响应的问题
先上代码:
- C/C++ code
HANDLE g_hEvent=NULL;BOOL g_Run=TRUE;TCHAR g_buf[0x100]={0};unsigned int WINAPI EvenThread(void *pVoid){ OutputDebugString(TEXT("start")); while(g_Run) { WaitForSingleObject(g_hEvent,INFINITE); if(g_Run) { OutputDebugString(g_buf); } } OutputDebugString(TEXT("end")); return 0;}//Start Eventvoid CTestSTLDlg::OnBnClickedButton12(){ if(g_hEvent==NULL) { g_Run=TRUE; g_hEvent=CreateEvent(NULL,FALSE,FALSE,TEXT("myTestEvent"));//自动重置信号 _beginthreadex(NULL,0,EvenThread,NULL,0,NULL); } else { OnBnClickedButton13(); }}//Stop Eventvoid CTestSTLDlg::OnBnClickedButton13(){ g_Run=FALSE; SetEvent(g_hEvent); CloseHandle(g_hEvent); g_hEvent=NULL;}//Notify Eventvoid CTestSTLDlg::OnBnClickedButton14(){ SetEvent(g_hEvent); GetDlgItemText(IDC_EDIT4,g_buf,0x100);}
这是一个MFC程序.
我生成的exe,然后运行了三个.
并且都调用了OnBnClickedButton12,即会在三个进程中都创建一个线程:EvenThread.
这时后,我点击任意一个exe中的OnBnClickedButton14()通知按键,都只有一个线程中的Event变成有信号状态,执行读取
g_buf的操作,因为WaitForSingleObject后变自动变为无信号,其它线程就无法再响应了.
也许你会说:设成人工重置信号不就行了,这样当然是可以都响应,但是这样它却会不停的响应的,而我只想响应一次就继续等待下一次通知.
所以想请教大家:
有没有办法,能让这些线程都响应这个事件,且只响应一次.
[解决办法]
CreateEvent每次创建的时候用一个单独的名字,这样就不会重复了
[解决办法]
用手动重置Event,线程唤醒执行了就退出
[解决办法]
这是一个MFC程序.
我生成的exe,然后运行了三个.
并且都调用了OnBnClickedButton12,即会在三个进程中都创建一个线程:EvenThread.
-----------
你三个进程直接需要通讯?不需要的话,你CreateEvent创建事件对象的时候指定名称为NULL就可以了
[解决办法]
方法1、人工重置 + PulseEvent,但微软说她这个孩子不是很靠谱。
方法2、试试SignalObjectAndWait,(微软新生的,原子的,我也没用过)
[解决办法]
没有很简单的办法,一个可靠的办法用共享内存,记住所有启动进程的pid,然后创建event的时候event名字用myTestEvent+pid,通知的时候每个pid对应的event都setevent一次。
这样简单可靠,不用考虑太多同步问题和进程崩溃的情况
[解决办法]
首先把命名事件改成手动状态,再定义一个全局量,给每个线程处理事件赋不同的权重,在线程内处理完后达到权重总和就恢复事件,没达到就说明有人还没处理就不要改变事件状态。
唉,现在的年轻人啊。
[解决办法]
使用带计数的Semaphore配合WaitForSingleObject。基本就能满足你的需求。
- C/C++ code
hSemaphore = CreateSemaphore( NULL, // default security attributes 0, // initial count cThreadCount, // maximum count NULL); // unnamed semaphore
[解决办法]
方法1、人工重置 + PulseEvent,但微软说她这个孩子不是很靠谱。
方法2、试试SignalObjectAndWait,(微软新生的,原子的,我也没用过)
都不好,你这个我问题的确有点难搞
人工重置和自动重置事件都不可以实现
你可以在进程启动的时候,注册消息,通过自动重置事件发送消息,三个进程都可以执行
这个是最好的了