构造函数
m_hMutex=CreateMutex(NULL,FALSE,"myMutex1211");
if(m_hMutex==NULL)
return;
m_hScanIOExit = CreateEvent(NULL,FALSE,FALSE,NULL);
DWORD dwThreadID ;
m_hScanIOThread = NULL;
m_hScanIOThread = CreateThread(NULL,0,CModbusUnit::SconIOToRam_Thread,(LPVOID) this,0,&dwThreadID) ;
if(NULL == m_hScanIOThread)
{
AfxMessageBox(_T("扫描IO线程创建失败!"));
}
析构函数
SetEvent(m_hScanIOExit);
if(m_hScanIOThread)
{
if(WaitForSingleObject(m_hScanIOThread,2000) != WAIT_OBJECT_0)
{
TerminateThread(m_hScanIOThread,-1);
}
}
CloseHandle(m_hScanIOExit) ;
线程
while(1)
{
//我看到他声明了一个事件、一个互斥,
    waitForSingleObject(m_hScanIOExit,0);//进入线程后先进入事件,然后在析构里释放。
    Sleep(300);Sleep(200);Sleep(100);Sleep(0);//睡眠4次
    WaitForSingleObject(m_hMutex);//进入互斥
     ……
    数据赋值……
    ……
    ReleaseMutex(m_hMutex);//释放互斥
}我是想问
1、他为什么声明一个事件一个互斥,只有一个互斥不够么?
2、再一个为什么要睡眠4次啊?如果想起到定时作用,再进入互斥之前sleep一次不就够了?
3、第三个就是Mutex和Event有什么区别。我在网上找了半天,都是复制的同一篇文章,我看的又不太明白,请明白人通俗易懂的讲讲啊!

解决方案 »

  1.   

    线程里,wait一个事件,这很正常
    但setevent放在析构函数里,这就太离谱了,更离谱的是,等到事件后,还sleep,还做了很多事
      

  2.   

    1. 需要知道具体的业务逻辑是什么
    2. 不知道是在干什么,得到自动重置事件对象以后,然后做Sleep(),猜想可能是得到互斥对象signal。
    3. 互斥对象和事件对象属于内核对象,利用内核对象进行线程同步,速度较慢。但利用互斥对象和事件对象这样的内核对象,可以跨进程,可以在多个进程中的各个线程间进行同步。
      

  3.   

    同一个线程里加多个锁的情况好像正常,资源不同,自然要加多个锁,睡眠4次,可能原来的代码中还有3个操作,或以后要再加3个操作,这里标记下怕以后忘掉加sleep
    第三个就是Mutex和Event有什么区别
    《Win32 多线程程序设计》(候捷译)
      

  4.   


    setevent放在析构函数里并不离谱,他的意图是,先setevent,通知线程:等到这个事件就可以退出了,然后接下来的代码是等待线程退出的,2秒钟线程还没结束就强行结束。但是线程里的代码,waitForSingleObject(m_hScanIOExit,0);他没判断返回值,就根本不知道线程该不该结束,是靠析构强行结束的。
      

  5.   

    Mutex和Event的区别,一个上面已经有人说了,互斥可以跨进程使用。event如果不是自动复位的,象LZ代码里的,手工复位的话,不能达到同步的目的,一个事件手工置位,是所有线程都接收到这个事件的。象这个代码里的意图就是他通知所有线程退出,只是代码里没有实现。线程里正确的代码应该是这样:
    while(1)
    {
        if(WaitForSingleObject(m_hScanIOExit,0) == WAIT_OBJECT_0)
          break;
        Sleep(600);//不需要睡眠4次,除非Sleep间另有代码要干什么事
        WaitForSingleObject(m_hMutex);//进入互斥
         ……
        数据赋值……
        ……
        ReleaseMutex(m_hMutex);//释放互斥
    }