效果
代码下载
代码
using System; using System.Diagnostics; using System.Threading; using System.Windows.Forms; namespace WindowsFormsApplication2 { public partial class Form1 : Form { public Form1() { InitializeComponent(); } private void BtnBeginInvoke_Click(object sender, EventArgs e) { //接收指令后马上开一个新线程去执行后立即返回,防止界面假死 System.Threading.ThreadPool.QueueUserWorkItem(o => DoByBeginInvoke()); Debug.WriteLine("BtnBeginInvoke_Click;Thread ID:{0}", Thread.CurrentThread.ManagedThreadId);//输出为9,表示UI线程的ID为9 } void DoByBeginInvoke() { //模拟执行一个花费时间很长的业务 System.Threading.Thread.Sleep(5000); Debug.WriteLine("DoByBeginInvoke;Thread ID:{0}", Thread.CurrentThread.ManagedThreadId);//输出为10,表示当前代码未在UI线程上执行 //专心更新界面 //此处的方法体依然在UI线程中完成执行,所以不要将其它非UI更新的操作放在里面,比如上面的模拟 LblCounter1.BeginInvoke(new Action(() => { LblCounter1.Text = (int.Parse(LblCounter1.Text) + 1).ToString(); Debug.WriteLine("LblCounter1.BeginInvoke;Thread ID:{0}", Thread.CurrentThread.ManagedThreadId);//输出为9,表示当前代码在UI线程上执行 })); LblCounter2.BeginInvoke(new Action(() => { LblCounter2.Text = (int.Parse(LblCounter2.Text) + 1).ToString(); Debug.WriteLine("LblCounter2.BeginInvoke;Thread ID:{0}", Thread.CurrentThread.ManagedThreadId);//输出为9,表示当前代码在UI线程上执行 })); } private void BtnSynchronizationContext_Click(object sender, EventArgs e) { //接收指令后马上开一个新线程去执行后立即返回,防止界面假死 System.Threading.ThreadPool.QueueUserWorkItem(DoBySynchronizationContext, System.Threading.SynchronizationContext.Current); Debug.WriteLine("BtnSynchronizationContext_Click;Thread ID:{0}", Thread.CurrentThread.ManagedThreadId);//输出为9,表示当前代码在UI线程上执行 } void DoBySynchronizationContext(object state) { //模拟执行一个花费时间很长的业务 System.Threading.Thread.Sleep(5000); Debug.WriteLine("DoBySynchronizationContext;Thread ID:{0}", Thread.CurrentThread.ManagedThreadId);//输出为10,表示当前代码未在UI线程上执行 var synchronizationContext=state as System.Threading.SynchronizationContext; synchronizationContext.Post(o => { //专心更新界面 //此处的方法体依然在UI线程中完成执行,所以不要将其它非UI更新的操作放在里面,比如上面的模拟 LblCounter1.Text = (int.Parse(LblCounter1.Text) + 1).ToString(); LblCounter2.Text = (int.Parse(LblCounter2.Text) + 1).ToString(); Debug.WriteLine("synchronizationContext.Post;Thread ID:{0}", Thread.CurrentThread.ManagedThreadId);//输出为9,表示当前代码在UI线程上执行 }, null); } } }
备注
线程执行时第一个控件被创建时,其SynchronizationContext.Current自动会被装上一个WindowFormsSynchronizationContext。
WindowFormsSynchronizationContext对象内部创建了一个Control,用于提供Invoke和BeginInvoke来帮助实现SynchronizationContext的Send或Post。