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

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

目前正在使用BeginInvoke,老实说它工作正常,但我一直听说你如何使用SynchronizationContext来做同样的事情。

哪个更受欢迎?

另外,从线程更新UI是不好的做法吗? 提出一个事件并让主要forms处理它或者还有其他更好的方法来做这件事会更好吗?

对于这个有点主观的问题感到抱歉,但是在线程领域有很多选择,我正在努力把握它们之间的差异以及它们各自适用的位置,以及为将来编写可读和可扩展代码的最佳实践。

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

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

SynchronizationContext.Current虽然通常与它关联的线程一样长。 它确实具有有限的寿命,因此最终存在相同的问题,但它比Control更可预测。

您是否考虑过使用Background Worker组件? 对于不应该占用UI的长时间运行任务,它是获得multithreadingfunction的简洁方法。 例如,您可以使用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