Control.Invoke 方法 (Delegate) :在拥有此控件的基础窗口句柄的线程上执行指定的委托。
Control.BeginInvoke方法 (Delegate) :在创建控件的基础句柄所在线程上异步执行指定委托。
Invoke和Begininvoke的使用有两种情况:
1. control中的Invoke、Begininvoke。
2. delegrate中的Invoke、Begininvoke。
一般,invoke表是同步、begininvoke表示异步,一般在支线线程中调用,但Invoke立即插入主线程中执行,而BeginInvoke要等主线程结束后才执行。
在多线程编程中,我们经常要在工作线程中去更新界面显示,而在多线程中直接调用界面控件的方法是错误的做法,Invoke 和 BeginInvoke 就是为了解决这个问题而出现的,使你在多线程中安全的更新界面显示。正确的做法是将工作线程中涉及更新界面的代码封装为一个方法,通过 Invoke 或者 BeginInvoke 去调用,两者的区别就是一个导致工作线程等待,而另外一个则不会。
/*Control的Invoke*/
private delegate void InvokeDelegate();
private void InvokeMethod()
{
//C代码段
}
private void butInvoke_Click(object sender,EventArgs e)
{
//A代码段.......
this.Invoke(new InvokeDelegate(InvokeMethod));
//B代码段......
}
执行顺序
(1)A在UI线程上执行完后,开始Invoke,Invoke是同步
(2)代码段B并不执行,而是立即在UI线程上执行InvokeMethod方法,即代码段C
(3)InvokeMethod方法执行完后,代码段B才在UI线程上继续执行
/*Control的BeginInvoke*/
private delegate voidBeginInvokeDelegate();
private void BeginInvokeMethod()
{
//C代码段
}
private void butBeginInvoke_Click(objectsender, EventArgs e)
{
//A代码段.......
this.BeginInvoke(new BeginInvokeDelegate(BeginInvokeMethod));
//B代码段......
}
执行顺序:
(1)A在UI线程上执行完后,开始BeginInvoke,BeginInvoke是异步
(2)InvokeMethod方法,即代码段C不会执行,而是立即在UI线程上执行代码段B。
(3)代码段B执行完后(就是说butBeginInvoke_Click方法执行完后),InvokeMethod方法,即代码段C才在UI线程上继续执行。
通过上述对比可知,invoke和begininvoke所提交的委托方法都是在主线程中执行的,但invoke和begininvoke的同步异步问题需要在子线程中来看。调用Invoke,invoke所提交的委托方法执行完成后,子线程才能继续执行;调用begininvoke,begininvoke所提交的委托方法后,子线程继续执行,不需要等待委托方法的完成。