最近正在学习《win32多线程程序设计》,这是其中一段重写消息循环的代码事例,以后可能用的上。

  while (!quit || gNumPrinting > 0)
{ // Wait for next message or object being signaled
DWORD dwWake;
dwWake = MsgWaitForMultipleObjects(
gNumPrinting,
gPrintJobs,
FALSE,
INFINITE,
QS_ALLEVENTS); if (dwWake >= WAIT_OBJECT_0 && dwWake < WAIT_OBJECT_0 + gNumPrinting)
{ // Object has been signaled
// Reorder the handle array so we do not leave
// empty slots. Take the handle at the end of
// the array and move it into the now-empty slot.
int index = dwWake - WAIT_OBJECT_0;
gPrintJobs[index] = gPrintJobs[gNumPrinting-1];
gPrintJobs[gNumPrinting-1] = 0;
gNumPrinting--;
SendMessage(hDlgMain, WM_THREADCOUNT, gNumPrinting, 0L);
} // end if
else if (dwWake == WAIT_OBJECT_0 + gNumPrinting)
{
while (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
{ // Get Next message in queue
if(hDlgMain == NULL || !IsDialogMessage(hDlgMain,&msg))
{
if (msg.message == WM_QUIT)
{
quit = TRUE;
exitCode = msg.wParam;
break;
} // end if
TranslateMessage(&msg);
DispatchMessage(&msg);
}
} // end while
}
} // end while

说明:

MsgWaitForMultipleObjects函数

该函数的特点是它不但可以等待内核对象,还可以等消息。也就是当有消息到来时,该函数也一样可以返回,并处理消息,这样就给了工作线程退出的机会。

DWORD MsgWaitForMultipleObjects(

DWORD nCount, //要等待的内核对象数目

LPHANDLE pHandles, //要等待的内核对象句柄数组指针

BOOL fWaitAll, //是等待全部对象还是单个对象

DWORD dwMilliseconds,//等待时间 

DWORD dwWakeMask );//等待的消息类型

下面就详解一下该函数的参数使用方法:

DWORD nCount:要等待的内核对象的数目。如果等待两个线程退出,则nCount=2;

LPHANDLE pHandles:要等待的内核对象句柄数组指针。

如果只要等待一个线程退出,则直接设置该线程句柄的指针即可:

MsgWaitForMultipleObjects(1,&m_pThread->m_hThread,…)

如果要等待两个线程退出,则使用方法为:

HANDLE hArray[2]={ m_pThread1->m_hThread , m_pThread2->m_hThread };

MsgWaitForMultipleObjects(2,hArray,…)

BOOL fWaitAll: TRUE-表示只有要等待的线程全部退出后,此函数才返回,

               FALSE-表示要等待的线程中任意一个退出了,或是有消息到达了,此函数均会返回。

在上面的OnButton2()函数中,我要等待一个线程退出,将fWaitAll设置为

FALSE,目的是无论是线程真的退出了,还是有消息到达了,该函数都能返回。

如果将该fWaitAll设置为TRUE,那么函数返回的唯一条件是线程退出了,即便

是有消息到来了,该函数也一样不会返回。

DWORD dwMilliseconds:等待的事件,单位是毫秒。可以设置为INFINITE,无

穷等待

DWORD dwWakeMask:等待的消息类型,通常可以设置为QS_ALLINPUT。此宏表示的是可以等待任意类型的消息。当然,也可以指定等待的消息类型。

#define QS_ALLINPUT        (QS_INPUT         | \

                            QS_POSTMESSAGE   | \

                            QS_TIMER         | \

                            QS_PAINT         | \

                            QS_HOTKEY        | \

                            QS_SENDMESSAGE)

返回值:DWORD dRet 通过函数返回值,可以得到一些有效信息。函数返回值依fWaitAll设置的不同而有所不同。下面是函数返回值的几种常见类型:

dRet = 0xFFFFFFFF :   表示函数调用失败,可用GetLastError()得到具体的出错信息;

dRet =WAIT_OBJECT_0+nCount:表示有消息到达了;

如果fWaitAll设置为TRUE

dRet = WAIT_OBJECT_0,表示所有等待的核心对象都激发了,或是线程都退出了;

如果fWaitAll设置为FALSE

dRet = WAIT_OBJECT_0 ~ WAIT_OBJECT_0+nCount-1:表示等待的内核对象被激发了,index=dRet - WAIT_OBJECT_0,表示hArray[]数组中索引为index的那个对象被激发了。

win32多线程-重写消息循环的更多相关文章

  1. win32编程中消息循环和WndProc()窗口过程函数

    原文地址:https://blog.csdn.net/zxxSsdsd/article/details/45504383 在win32程序的消息循环函数中  while (GetMessage (&a ...

  2. Win32消息循环机制等【转载】http://blog.csdn.net/u013777351/article/details/49522219

    Dos的过程驱动与Windows的事件驱动 在讲本程序的消息循环之前,我想先谈一下Dos与Windows驱动机制的区别: DOS程序主要使用顺序的,过程驱动的程序设计方法.顺序的,过程驱动的程序有一个 ...

  3. 什么是消息循环,一个简单的win32程序如何运行?

    预备知识 1.什么是句柄? (HANDLE) 在win32编程中有各种句柄,那么什么是句柄呢? #define DECLARE_HANDLE(name) struct name##_ { int un ...

  4. Win32编程API 基础篇 -- 4.消息循环

    消息循环 理解消息循环 为了编写任何即使是最简单的程序,了解windows程序的消息循环和整个消息发送结构是非常有必要的.既然我们已经尝试了一点消息处理的东西,我们应该对整个程序有更深入的理解,如果你 ...

  5. Win32 SDK 编程开始, 创建窗口, 消息的处理, 消息循环

    Windows SDK 编程的一般步骤为: 1. 注册窗口类, 使用到的结构 WNDCLASSEX, 函数 RegisterClassEx. 2. 创建窗口, 函数 CreateWindowEx. 3 ...

  6. Android的消息循环机制 Looper Handler类分析

    Android的消息循环机制 Looper Handler类分析 Looper类说明   Looper 类用来为一个线程跑一个消息循环. 线程在默认情况下是没有消息循环与之关联的,Thread类在ru ...

  7. 深入浅出Win32多线程程序设计之基本概念

    一.深入浅出Win32多线程程序设计之基本概念[转] 引言 从单进程单线程到多进程多线程是操作系统发展的一种必然趋势,当年的DOS系统属于单任务操作系统,最优秀的程序员也只能通过驻留内存的方式实现所谓 ...

  8. 深入探讨MFC消息循环和消息泵

    首先,应该清楚MFC的消息循环(::GetMessage,::PeekMessage),消息泵(CWinThread::PumpMessage)和MFC的消息在窗口之间的路由是两件不同的事情.在MFC ...

  9. 多线程学习:win32多线程编程基本概念(转)

    一.定义: 1.进程和线程的区别 进程:是程序的执行过程,具有动态性,即运行的程序就叫进程,不运行就叫程序 ,每个进程包含一到多个线程.线程:系统中的最小执行单元,同一进程中有多个线程,线程可以共享资 ...

随机推荐

  1. Linux进程和线程的比較

    进程与线程 參考:http://www.cnblogs.com/blueclue/archive/2010/07/16/1778855.html 首先比較Linux进程和线程的创建的差别,以此展开: ...

  2. JS实现倒计时网页自动跳转(如404页面经常使用到的)

    在web前端设计中,我们经常会遇到需要实现页面倒计时跳转的功能,例如在404页面中也会经常使用到此功能,那么如何实现呢,其实实现方法很简单,实现代码如下:<title>JS倒计时网页自动跳 ...

  3. Linux C语言操作MySQL

    原文:Linux C语言操作MySQL 1.MySQL数据库简介 MySQL是一个开源码的小型关系数据库管理系统,体积小,速度快,总体成本低,开源.MySQL有以下特性: (1) 使用C和C++编写, ...

  4. Cocos2d-x 3.0final 终结者系列教程12-Vector&amp;map&amp;value

    北京时间昨天下午,温40度.中午12:16我来到了篮球场点.思维1分钟决定开站 转球: 我和另一个3队友半开始, 我手中的球的那一刻我突然火爆球不稳,突然问,淡淡的味道橡胶和烧烤的味道混合. 个腾空跳 ...

  5. 快速构建Windows 8风格应用18-基础控件I

    原文:快速构建Windows 8风格应用18-基础控件I 本篇博文主要介绍Windows 8风格应用开发中常用的几种基础控件. ProgressRing: ProgressRing控件常见的效果图: ...

  6. sql 中如何取出指定行: Row_Number

    原文:sql 中如何取出指定行: Row_Number ROW_NUMBER (Transact-SQL) USE AdventureWorks2008R2;GOWITH OrderedOrders ...

  7. Linux下查看使用频率最高的十个命令

    这个shell是在linux吧一个小伙伴发的,链接已找不到,挺有意思的,隔段时间运行一次,可以看看自己最近都干了什么. [shell] history | awk '{CMD[$2]++;count+ ...

  8. leetcode第17题--4Sum

    Problem:Given an array S of n integers, are there elements a, b, c, and d in S such that a + b + c + ...

  9. Bootstrap Paginator分页插件

    Bootstrap Paginator分页插件使用示例 最近做的asp.netMVC项目中需要对数据列表进行分类,这个本来就是基于bootstrap开发的后台,因此也就想着bootstrap是否有分页 ...

  10. 使用UDL文件来测试SQL Server数据库连接

    原文 来自http://www.2cto.com/database/201308/234427.html 使用UDL测试SQL Server连接问题   做数据库经常会遇到SQL Server连接的问 ...