如何正确地在WinForms中创建多线程GUI应用程序?
如何正确地在WinForms中创建多线程GUI应用程序?
我来自C背景,目前我想制作一个具有响应式GUI和长时间运行的工作线程的小型WinForms实用工具。
GUI是常规的Form1派生类,具有进度指示器等功能,工作线程是new System.Threading.Thread();
这种类型。
在C++中,一切都很简单,在.NET中,我不知道该怎么做。
有没有一种类似于PostMessage的方法来更新数据?我应该在主线程上启动一个定时器来读取受共享锁保护的结构,还是有其他方法?我看过多个关于委托的文档,但在阅读了10篇不同的文章后,它们似乎并不起作用,也许是因为我有一个工作线程<->GUI的关系,而不是GUI<->GUI的关系。
所有GUI相关的内容都在GUI类中,所有工作线程相关的内容都在它自己的工作线程类中。在托管世界中,最佳实践是什么?
在WinForms中正确地创建线程化的GUI应用程序是一个常见的问题。有多种方法可以解决这个问题,但简单来说,可以采取以下步骤:
1. 启动一个线程。
2. 使用InvokeRequired和Invoke()方法返回到GUI线程。
另外,BackgroundWorker类提供了一种更简单的方法。
如果我理解正确的话,在这种情况下,数据处理库拥有GUI,它会不时地更新GUI。我所寻找的是GUI<->[进度存储]<->逻辑和数据层之间的通信。GUI启动数据处理,但会定期检查事件,以查看是否有新的进度存储数据可用,并根据需要更新GUI元素。这种情况是否可行?
然后启动一个新线程,使用一个可以被GUI直接访问的共享对象(这样GUI可以插入内容)和新线程。如果需要,可以发出信号通知线程有更新,线程会处理新的更新并调用Control.Invoke()方法来更新GUI。
是的,这就是我寻找的,但是如果.NET中没有PostMessage架构,我如何通知GUI?
你只需要使用Control.Invoke(YourFunction)这一行代码,其他的PostMessage等操作都在后台自动完成。
我尝试将Form1的引用传递给工作线程,然后调用MethodInvoker action = delegate { Form1.UpdateGUI(); }; Form1.BeginInvoke(action);。但仍然会出现从错误线程调用的异常。
在WinForms中正确创建线程化的GUI应用程序?
在WinForms中,我们想要创建一个具有线程化功能的GUI应用程序。但是,我们需要知道在使用WinForms时,应该使用哪种方法来实现线程化的GUI应用程序。
以下是一些常见的方法:
1. 使用BackgroundWorker:使用BackgroundWorker类可以在后台线程上执行操作,并在完成后更新GUI。它提供了方便的事件和方法来处理进度报告和取消操作。
2. 使用Control.Invoke:Control.Invoke方法允许在GUI线程上执行操作。这在需要在后台线程中执行操作并更新GUI时非常有用。
3. 使用SynchonizationContext:SynchonizationContext类提供了一种在指定线程上执行操作的方法。它可以用来执行GUI操作并确保线程安全。
4. 使用Task Parallel Library(System.Threading.Tasks):Task Parallel Library(TPL)提供了一种简化并行编程的方法。它可以与WinForms一起使用,以实现线程化的GUI应用程序。
5. 使用Rx:Rx(Reactive Extensions)是一种用于编写异步和事件驱动程序的库。它提供了一种简化处理异步操作的方法,并可以与WinForms一起使用。
6. 不要使用Thread.Start或ThreadPool:在WinForms中,不推荐直接使用Thread.Start或ThreadPool来创建线程。这是因为这种方法过于低级,可能会导致线程安全和其他问题。
以上是一些常见的方法来创建线程化的GUI应用程序。根据个人的需求和偏好,选择合适的方法来实现线程化的GUI应用程序。