我应该使用 Invoke 或 SynchronizationContext 从另一个线程更新表单控件吗?

发布于 2024-12-05 20:12:06 字数 355 浏览 0 评论 0原文

尝试从其他线程更新 UI 控件。

目前正在使用 BeginInvoke,老实说它工作正常,但我不断听说如何使用 SynchronizationContext 来完成同样的事情。

哪个是首选?

另外,从线程更新 UI 是不好的做法吗?引发事件并让主窗体处理它会更好吗?还是还有其他更好的方法来做到这一点?

很抱歉这个有点主观的问题,但是线程世界中有很多选择,我试图掌握它们的差异以及它们各自的适用范围,以及为未来编写可读和可扩展代码的最佳实践。

编辑:现在我还看到还有 TaskScheduler.FromCurrentSynchronizationContext 路线..这么多选择 x_x

Trying to wrap my head around updating UI controls from other threads.

Currently using BeginInvoke and honestly it's working fine but I keep hearing about how you can use SynchronizationContext as well to do the same thing.

Which is preferred?

Also, is it bad practice to update the UI from a thread? Would it be better to raise an event and have the main form handle it instead or are there other preferable ways to do that as well?

Sorry for the somewhat subjective question but there are so many options in the world of threading and I'm trying to grasp their differences and where each of them are applicable, along with best practices for writing readable and extendable code for the future.

Edit: Also now I see there is the TaskScheduler.FromCurrentSynchronizationContext route as well.. So many choices x_x

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

梅倚清风 2024-12-12 20:12:06

我更喜欢 SynchronizationContext 而不是 Control.InvokeControl.Invoke 的危险在于拥有的 Control 存在生命周期问题。如果在您尝试Invoke 时控制被释放,那么它会影响调用成功的能力。当对话框关闭、视图移动等时会发生这种情况...

SynchronizationContext.Current 不过通常与它关联的线程一样存在。它确实有有限的生命周期,因此最终会出现相同的问题,但它比 Control 更可预测。

I prefer SynchronizationContext over Control.Invoke. The danger of Control.Invoke is that there is a lifetime issue with the owning Control. If the Control is disposed while you are trying to Invoke on it then it compromises the ability of the call to succeed. This happens when dialogs are closed, views shifted, etc ...

SynchronizationContext.Current though generally lives as long as the thread it's associated with. It does have a finite lifetime and hence ultimately the same problems but it's a bit more predictable than a Control.

箜明 2024-12-12 20:12:06

您是否考虑过使用后台工作组件?对于不应该占用 UI 的长时间运行的任务,这是一种获得多线程功能的干净而简单的方法。例如,您可以使用 ProgressChanged 事件和后台工作程序对 UI 执行更新,并且后台工作程序类将确保创建 BW 的线程是执行 ProcessChanged 和 WorkComplete 事件的线程。因此,如果您从 UI 制作了 BW 并使其开始工作,那么您可以从那里安全地更新 UI。

这是 MS 的一篇简短文章
http://msdn.microsoft.com/en -us/library/cc221403%28v=vs.95%29.aspx

另一个非常好的链接
http://www.albahari.com/threading/part3.aspx#_BackgroundWorker

Have you looked into using a Background Worker component? For long running tasks that shouldn't tie up the UI it is a clean and easy way to get multithreading capabilites. For instance you can perform updates to the UI using the ProgressChanged Event and the background worker and the background worker class will ensure that the thread that created the BW is the one that executes the ProcessChanged and WorkComplete event. So if you made the BW from the UI and set it off to work then you can update the UI safely from there.

Here's a quick article from MS
http://msdn.microsoft.com/en-us/library/cc221403%28v=vs.95%29.aspx

Another really good link
http://www.albahari.com/threading/part3.aspx#_BackgroundWorker

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文