我有一个带有报表模式 ListView 的 Windows 窗体。对于视图中的每个项目,我需要执行长时间运行的操作,其结果是一个数字。
我在本机 win32 中执行此操作的方法是为每个项目创建一个工作线程(天真地;当然我不会创建无限数量的线程),然后在线程句柄数组上创建 MsgWaitForMultipleObjects() 。每次计算完成后,线程都会发出信号,主 UI 线程将被唤醒并更新。同时,我们会泵送消息,以便 UI 线程保持响应。
任何人都可以提供一个示例来说明这在 C# 中如何工作吗?我查看了 Monitor 对象,它似乎不是我想要的,或者它是否在阻塞时泵送消息?
Thanks.
编辑:似乎 WaitHandler.WaitAny() 实际上可能会泵送消息。看克布鲁姆的论文 http://blogs.msdn.com/cbrumme/archive/2004/02/02/66219.aspx关于 CLR 中的消息泵。
让您的主线程创建一个管理器线程。你可以使用后台工作者 http://msdn.microsoft.com/en-us/library/system.componentmodel.backgroundworker.aspx为了这。该管理器线程为 ListView 中的每个项目启动一个工作线程。这将允许您的 UI 在后台线程处理时继续响应用户输入而不会挂起。
现在的问题是如何等待每个工作线程完成。不幸的是,我一直无法找到一种方法来获取线程句柄System.Threading.Thread
对象。我并不是说没有办法做到这一点;我并不是说没有办法做到这一点。我只是还没找到一个。另一个复杂的方面是System.Threading.Thread
类是密封的,因此我们无法从它派生来提供某种“句柄”。
这是我使用的地方手动重置事件 http://msdn.microsoft.com/en-us/library/system.threading.manualresetevent.aspx.
假设每个工作线程只是一个ThreadPool
线。管理的BackgroundWorker
创建一个ManualResetEvent
ListView 中每个项目的对象。作为BackgroundWorker
启动每个ThreadPool
线程,通过ManualResetEvent
作为一个论点QueueUserWorkItem功能 http://msdn.microsoft.com/en-us/library/4yd16hza.aspx。然后,就在每个之前ThreadPool
线程退出时,设置ManualResetEvent
object.
The BackgroundWorker
然后线程可以把所有的ManualResetEvent
数组中的对象并使用以下命令等待该数组WaitHandle.WaitXXX功能 http://msdn.microsoft.com/en-us/library/system.threading.waithandle_members.aspx。当每个线程完成时,您可以使用BackgroundWorker
的事件来更新 UI 或者您可以使用Control.Invoke()
更新 UI 的技术(参见 Marc Gravell 的回答here https://stackoverflow.com/questions/253138/anonymous-method-in-invoke-call).
希望这可以帮助。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)