zoukankan      html  css  js  c++  java
  • 通过Event事件正确结束线程

      
    步骤:
    1. 首先声明一个全局的Event对象
           HANDLE hRequestExitEvent = FALSE;
    2. 在主线程中创建这个Event对象
           hRequestExitEvent = CreateEvent(NULL, TRUE, false, NULL);
           注意:此处的第三个参数应该使用false,因为如果使用true在事件创建开始就是处于
        激发状态,这样就立刻结束线程了,所以此处应该使用false作参数
    3. 在线程函数中使用如下语句来不断探测Event对象的状态并确定是否退出线程
           WaitForSingleObject(hRequestExitEvent, 0)
           注意:此处的此处的第二个参数为0,这里使用了WaitForSingleObject()函数一个很重
    要的用途,设定这个参数为0,是你能够检查handle的状态并立刻返回,没有片刻停留,
    如果handle已经备妥,这个函数会成功并传回WAIT_OBJET_0,否则这个函数立刻传
    回WAIT_TIMEOUT。
    4. 在主线程中需要结束该线程的地方调用如下语句设置Event对象为激发状态
           SetEvent(hRequestExitEvent);
           这样便可安全的结束一个线程
     
    参考代码:
    说明:该实例代码参考《Win32 多线程程序设计(候捷译)》中的THRDTERM程序,该程序创建两个线程,周期性地检查一个Event对象,以决定要不要结束自己。
    #define WIN32_LEAN_AND_MEAN
    #include <stdio.h>
    #include <stdlib.h>
    #include <windows.h>
    #include <time.h>
    #include "MtVerify.h"
     
    DWORD WINAPI ThreadFunc(LPVOID);
     
    HANDLE hRequestExitEvent = FALSE; //设置全局EVENT对象
     
    int main()
    {
        HANDLE hThreads[2];
        DWORD dwThreadId;
        DWORD dwExitCode = 0;
        int i;
     
        hRequestExitEvent = CreateEvent(
            NULL, TRUE, false, NULL);   // 创建Event对象
     
        for (i=0; i<2; i++)
            MTVERIFY( hThreads[i] = CreateThread(NULL,
                0,
                ThreadFunc,
                (LPVOID)i,
                0,
                &dwThreadId )
            );
     
        // Wait around for awhile, make
        // sure the thread is running.
        Sleep(1000);
     
        SetEvent(hRequestExitEvent); //设置Event对象为激发状态,结束线程
          
    WaitForMultipleObjects(2, hThreads, TRUE, INFINITE); // 等待两个线程都成为激发状
    态,可以保证线程都已安全地离开。
     
           printf("1234/n");
     
        for (i=0; i<2; i++)
            MTVERIFY( CloseHandle(hThreads[i]) );
     
        return EXIT_SUCCESS;
    }
     
     
    DWORD WINAPI ThreadFunc(LPVOID p)
    {
        int i;
        int inside = 0;
     
        UNREFERENCED_PARAMETER(p);
     
        /* Seed the random-number generator */
        srand( (unsigned)time( NULL ) );
     
        for (i=0; i<1000000; i++)
        {
            double x = (double)(rand())/RAND_MAX;
            double y = (double)(rand())/RAND_MAX;
            if ( (x*x + y*y) <= 1.0 )
                inside++;
            if (WaitForSingleObject(hRequestExitEvent, 0) != WAIT_TIMEOUT) // 判断Event对
               象是否为激发状态,从而决定是否退出
            {
                printf("Received request to terminate/n");
                return (DWORD)-1;
            }
        }
        printf("PI = %.4g/n", (double)inside / i * 4);
        return 0;
    }
  • 相关阅读:
    BEC listen and translation exercise 16
    BEC listen and translation exercise 15
    BEC listen and translation exercise 14
    PyQt(Python+Qt)学习随笔:toolButton的popupMode属性
    PyQt(Python+Qt)学习随笔:实现toolButton与Action的关联
    PyQt(Python+Qt)学习随笔:Qt Designer中连接Action和槽函数
    PyQt(Python+Qt)学习随笔:Qt Designer中怎么给toolBar添加按钮
    PyQt(Python+Qt)学习随笔:快速理解Qt 中Action是什么
    PyQt(Python+Qt)实战:使用QCamera、QtMultimedia等实现摄像头拍照
    第15.13节 PyQt(Python+Qt)入门学习:Qt Designer的Spacers部件详解
  • 原文地址:https://www.cnblogs.com/zhangyunlin/p/6168011.html
Copyright © 2011-2022 走看看