C#:Invoke 和 BeginInvoke 的真正涵义

BeginInvoke 方法真的是新开一个线程进行异步调用吗?

参考以下代码:

public delegate void treeinvoke();
private void UpdateTreeView()
{MessageBox.Show(System.Threading.Thread.CurrentThread.Name);
}
private void button1_Click(object sender, System.EventArgs e)
{System.Threading.Thread.CurrentThread.Name = "UIThread";treeView1.BeginInvoke(new treeinvoke(UpdateTreeView));
}

看看运行结果,弹出的对话框中显示的是 UIThread,这说明 BeginInvoke 所调用的委托根本就是在 UI 线程中执行的。

既然是在 UI 线程中执行,又何来“异步执行”一说呢?

我们再看看下面的代码:

public delegate void treeinvoke();
private void UpdateTreeView()
{MessageBox.Show(Thread.CurrentThread.Name);
}
private void button1_Click(object sender, System.EventArgs e)
{Thread.CurrentThread.Name = "UIThread";Thread th = new Thread(new ThreadStart(StartThread));th.Start();
}
private void StartThread()
{Thread.CurrentThread.Name = "Work Thread";treeView1.BeginInvoke(new treeinvoke(UpdateTreeView));
}

再看看运行结果,弹出的对话框中显示的还是 UIThread,这说明什么?这说明 BeginInvoke 方法所调用的委托无论如何都是在 UI 线程中执行的。

那 BeginInvoke 究竟有什么用呢?

在多线程编程中,我们经常要在工作线程中去更新界面显示,而在多线程中直接调用界面控件的方法是错误的做法,具体的原因可以在看完我的这篇之后看看这篇:在多线程中如何调用Winform,如果你是大牛的话就不要看我这篇了,直接看那篇吧,反正那篇文章我没怎么看懂。

Invoke 和 BeginInvoke 就是为了解决这个问题而出现的,使你在多线程中安全的更新界面显示。

正确的做法是将工作线程中涉及更新界面的代码封装为一个方法,通过 Invoke 或者 BeginInvoke 去调用,两者的区别就是一个导致工作线程等待,而另外一个则不会。

而所谓的“一面响应操作,一面添加节点”永远只能是相对的,使 UI 线程的负担不至于太大而以,因为界面的正确更新始终要通过 UI 线程去做,我们要做的事情是在工作线程中包揽大部分的运算,而将对纯粹的界面更新放到 UI 线程中去做,这样也就达到了减轻 UI 线程负担的目的了。

而在那段更新树节点的代码中,其实唯一起作用的代码是:System.Threading.Thread.Sleep(100);,它使 UI 线程有了处理界面消息的机会,只要以下的代码就可以很好的工作了。

private void button1_Click_(object sender, System.EventArgs e)
{TreeNode tn;for(int i=0;i<100000;i++){tn=new TreeNode (i.ToString());this.treeView1.Nodes[0].Nodes.Add(tn);if (i%100 == 0) Application.DoEvents();}
}

C#:Invoke 和 BeginInvoke 的真正涵义相关推荐

  1. Invoke 和 BeginInvoke 的真正涵义

    BeginInvoke 方法真的是新开一个线程进行异步调用吗? 参考以下代码: public delegate void treeinvoke(); private void UpdateTreeVi ...

  2. C#中Invoke 和 BeginInvoke的涵义和区别

    BeginInvoke 方法真的是新开一个线程进行异步调用吗? 参考以下代码: public delegate void treeinvoke(); private void UpdateTreeVi ...

  3. 委托的Invoke 和 BeginInvoke 与Control的Invoke和BeginInvoke(转-因为写得很好)

    原文地址:http://www.cnblogs.com/worldreason/archive/2008/06/09/1216127.html Invoke and BeginInvoke Invok ...

  4. c# Invoke和BeginInvoke 区别

    转自http://www.cnblogs.com/c2303191/articles/826571.html Control.Invoke 方法 (Delegate) :在拥有此控件的基础窗口句柄的线 ...

  5. c# Invoke和BeginInvoke 区别详解

    Control.Invoke 方法 (Delegate):在拥有此控件的基础窗口句柄的线程上执行指定的委托. Control.BeginInvoke 方法 (Delegate) :在创建控件的基础句柄 ...

  6. c# Invoke和BeginInvoke

    *************************************************** 更多精彩,欢迎进入:http://shop115376623.taobao.com ****** ...

  7. C#中Invoke 和 BeginInvoke 的区别

    Invoke 和 BeginInvoke 的真正涵义 .在多线程中如何调用Winform Control.Invoke 方法 (Delegate) :在拥有此控件的基础窗口句柄的线程上执行指定的委托. ...

  8. Invoke and BeginInvoke BeginInvoke和EndInvoke方法 (转)3

    近日,被Control的Invoke和BeginInvoke搞的头大,就查了些相关的资料,整理如下.感谢这篇文章对我的理解Invoke和BeginInvoke的真正含义 . (一)Control的In ...

  9. C# Invoke和BeginInvoke(1)

    近日,被Control的Invoke和BeginInvoke搞的头大,就查了些相关的资料,整理如下.感谢这篇文章对我的理解Invoke和BeginInvoke的真正含义 . (一)Control的In ...

最新文章

  1. 【GVA】gorm多对多many2many删除数据的同时级联删除关联中间表中的关联数据
  2. python多线程怎么写日志_Python日志记录在多进程下的使用
  3. mysql 两列互换
  4. 【微信网页直接下载app】微信跳转-微信浏览器中直接唤起本地浏览器和App
  5. 弹出键盘布局上移_评测 | 别买了HHKB键盘不知道这些新功能!
  6. JAVA 获取操作系统属性
  7. 【Python3网络爬虫开发实战】 1.2.2-Selenium的安装
  8. python之log日志模块
  9. Widget、MainWindow和Dialog的选择使用
  10. 数据结构和算法 D2
  11. 181029每日一句
  12. matlab coefs,MATLAB小波分析工具箱常用函数
  13. win10开启Linux蓝屏,win10启动蓝屏_Win10怎么开启蓝屏记录
  14. 对计算机硬盘格式化,电脑硬盘格式化和快速格式化的区别
  15. 手机只能上QQ不能看网页
  16. [Unity2D入门教程]简单制作仿植物大战僵尸游戏之③完善Defender植物和Attacker的相关细节(脚本,碰撞体)
  17. Netty :仿写微信 IM 即时通讯系统
  18. React Native入门——布局实践:开发京东客户端首页
  19. php中$this-是什么意思?
  20. oracle灾备同步_浅析Oracle数据库的三种灾备技术

热门文章

  1. 新出免费字体——阿里巴巴普惠字体(附安装使用教程)
  2. @Compoment
  3. 抓取html指定标签内容,javascript怎样获取某个标签的内容?
  4. WIN7修改“桌面”存储位置
  5. 【个人博客】Astro 快速搭建个人博客
  6. 【数据结构】之两栈共享空间(C语言)
  7. HTML5 参考手册 ———— 颜色名
  8. 编程语言:C语言网络资源
  9. 适合穷人挣钱最快的方法
  10. ps计算机网络海报,PS教程:Photoshop制作星空云海创意海报