Windows 线程何时需要消息循环,为啥?

Posted

技术标签:

【中文标题】Windows 线程何时需要消息循环,为啥?【英文标题】:When does a Windows thread need a message loop and why?Windows 线程何时需要消息循环,为什么? 【发布时间】:2013-04-17 08:08:05 【问题描述】:

什么时候需要在 Windows 应用程序中使用消息循环?

例如,对于 Windows 服务,我是否需要为我创建的每个线程或仅用于主服务进程的消息循环?

while(true)

    GetMessage(&messageHandle, 0, 0, 0);
    DispatchMessage(&messageHandle);

【问题讨论】:

【参考方案1】:

每个本地 Windows 程序都至少包含一个消息循环(通常称为“消息泵”),就像您举的例子一样。

这是为了能够处理由程序本身、其他应用程序或操作系统发起的 Windows 事件。

Windows 事件示例可以是计时器、套接字通信、GUI 操作、剪贴板等。

许多 API 和框架为您实现了消息循环。这将取决于您在特定情况下使用的内容。

(查看this Stack Overflow question 中的答案以获取有关消息循环/消息泵的更多信息。)

现在回到问题的要点:许多或大多数程序都可以在一个消息循环中正常工作。您需要多个事件的情况通常是处理 Windows 事件可能需要很长时间(即它锁定当前线程)并且有些要求也需要您继续处理新的窗口事件。我能想到两个具体的例子:

    一个是在 GUI 应用程序中,您正在显示一个模式对话框(这通常会冻结主消息泵并为对话框启动一个新的) 由于外部依赖性和处理新 I/O 事件的及时性,处理 I/O 事件可能需要很长时间的某种服务至关重要

在 (1) 中,这通常是您使用的 GUI 框架的结果,而不是您必须明确执行的操作。在 (2) 中,更好的处理方法是异步“完成工作”每个事件,而不是阻塞消息泵。

总之:这取决于。 :-) 在大多数情况下,您不需要使用多个消息循环,但如果必须,就这样做!

【讨论】:

【参考方案2】:

应用:

本质上,当线程要创建和管理窗口时。这包括支持 COM STA 等的“隐藏”窗口。

没有窗口,没有窗口消息,不需要消息循环。

服务:

服务管理器需要处理服务消息,因此需要一个用于启动/停止/什么的服务消息循环。

对于服务中启动的其他线程,不需要消息循环。

【讨论】:

服务中不需要消息循环。服务管理器将从它自己的线程中调用您的 OnStart / OnStop 等。当然,您可能需要自己的循环,但这不是必需的。

以上是关于Windows 线程何时需要消息循环,为啥?的主要内容,如果未能解决你的问题,请参考以下文章

工作线程没有消息循环(MFC、windows)。我们可以让它接收消息吗?

windows 消息循环和窗口与线程关系

线程之间的通讯问题

使用 Windows 消息循环的回调实现

Windows下多线程编程

Windows下多线程编程