关于多线程的一个例子(UI实时显示)
在开发Window应用程序的时候,经常需要在界面上显示出已经执行到什么步骤了,拿一个简单例子来说,创建一个Winform程序,在窗体上访一个Button和一个Label,点击Button时做100次循环,在Label上实时显示当前循环的次数。一种简单的做法就是使用Application.DoEvents,代码如下:
private void btnTest_Click(object sender, EventArgs e) {for (int i = 0; i < 100; i++){Thread.Sleep(100);label1.Text = i + "/100";Application.DoEvents();} }
上面的代码如果将Application.DoEvents();去掉当点击Button时,程序会卡住,直到这个循环执行完成,当这个循环足够大时是不能忍受的。不过小数据量用Application.DoEvents()还行,数据量大了使用Application.DoEvents()就会带来性能的问题。所以Application.DoEvents()要慎用,在大数据量的时候可以使用多线程解决。如下:
private void btnTest_Click(object sender, EventArgs e) {Thread thread = new Thread(new ThreadStart(DoWork));thread.Start(); } private void DoWork() {for (int i = 0; i < 100; i++){Thread.Sleep(100);label1.Text = i + "/100";} }
嗯?出现异常了是吧,没错上面的代码运行后后会出现“线程间操作无效: 从不是创建控件“label1”的线程访问它。”的异常。关于什么原因造成的,大家可以google一下。不过上面代码在vs03中貌似可以正常运行。将代码改成下面这样就可以正常运行了:
private void btnTest_Click(object sender, EventArgs e) {Thread thread = new Thread(new ThreadStart(DoWork));thread.Start(); } private void DoWork() {for (int i = 0; i < 100; i++){Thread.Sleep(100);this.Invoke(new Action<string>(this.ChangeLabel),i.ToString());} } private void ChangeLabel(string i) {label1.Text = i + "/100"; }
如果嫌多写一个ChangeLabel方法费事,可以写成匿名方法的形式,如下:
private void btnTest_Click(object sender, EventArgs e) {Thread thread = new Thread(new ThreadStart(DoWork));thread.Start(); } private void DoWork() {for (int i = 0; i < 100; i++){Thread.Sleep(100);this.Invoke(new Action(delegate(){label1.Text=i+"/100";}));} }
同样可以使用匿名方法的方式将DoWork方法也去掉:
private void btnTest_Click(object sender, EventArgs e) {Thread thread = new Thread(new ThreadStart(delegate() {for (int i = 0; i < 100; i++){Thread.Sleep(100);this.Invoke(new Action(delegate() { label1.Text = i + "/100"; }));}}));thread.Start(); }
如果想传参数到Dowork方法中,那么就不能使用ThreadStart类了,应该使用ParameterizedThreadStart类,如下:
private void btnTest_Click(object sender, EventArgs e) {string name = "oec2003";Thread thread = new Thread(new ParameterizedThreadStart(DoWork));thread.Start(name); } private void DoWork(object name) {for (int i = 0; i < 100; i++){Thread.Sleep(100);this.Invoke(new Action(delegate(){label1.Text=name+":"+ i+"/100";}));} }
同样我们也可以使用线程池的方式来实现
private void btnTest_Click(object sender, EventArgs e) {ThreadPool.QueueUserWorkItem(new WaitCallback(DoWork)); } private void DoWork(object o) {for (int i = 0; i < 100; i++){Thread.Sleep(100);this.Invoke(new Action(delegate(){label1.Text=i+"/100";}));} }
使用匿名方法的方式:
private void btnTest_Click(object sender, EventArgs e) {ThreadPool.QueueUserWorkItem(new WaitCallback(delegate(object o){for (int i = 0; i < 100; i++){Thread.Sleep(100);this.Invoke(new Action(delegate() { label1.Text = i + "/100"; }));}})); }
平时做Windows应用程序很少,对多线程理解也不是特别深入,有什么不对的地方往大家指正。
返回开篇(索引)
转载于:https://www.cnblogs.com/oec2003/archive/2009/12/20/1628412.html
关于多线程的一个例子(UI实时显示)相关推荐
- 项目实例改编:利用structs2的action 实时显示图片、pdf和其他内容的框架抽取。(转)...
转自:http://www.verydemo.com/demo_c167_i1382.html 针对:预览文件(图片,PDF)文件来源为action中的inputStream 重点: structs2 ...
- QT5完成一个数据实时显示控制的Demo
使用QT5完成一个数据实时显示控制的Demo TestUiTheme-pro main.cpp mainwindow.h mainwindow.cpp themewidget.h themewidge ...
- python串口数据绘图_使用Python串口实时显示数据并绘图的例子
使用pyserial进行串口传输 一.安装pyserial以及基本用法 在cmd下输入命令pip install pyserial 注:升级pip后会出现 "'E:\Anaconda3\Sc ...
- python读取串口数据 绘图_使用Python串口实时显示数据并绘图的例子
使用pyserial进行串口传输 一.安装pyserial以及基本用法 在cmd下输入命令pip install pyserial 注:升级pip后会出现 "'E:Anaconda3Scri ...
- 使用QT5完成一个数据实时显示控制的Demo
使用QT5完成一个数据实时显示控制的Demo TestUiTheme-pro main.cpp mainwindow.h mainwindow.cpp themewidget.h themewidge ...
- python+tkinter+threading制作多线程简易音乐播放器(自动播放,上一曲,下一曲,播放,暂停,实时显示歌曲名并能自动切换歌曲的功能)
https://blog.csdn.net/qq_41962782/article/details/80106158 小弟是小白因大作业,在此博文的基础上,我增加了歌曲目录的选择,自动播放,实时显示歌 ...
- 测试基于STM32的ADIS16405评估板,并在匿名四轴上实时显示3轴陀螺仪+3轴加速度计+3轴磁力计 波形。本文最后还公开一个基于C# 的串口波形显示客户端源码。
标题:测试基于STM32的ADIS16405评估板,并在匿名四轴上实时显示3轴陀螺仪+3轴加速度计+3轴磁力计 波形.本文最好还公开一个基于C# 的串口波形显示客户端源码. 这里附上该评估板的原理图和 ...
- 使用Uploadify实现上传图片生成缩略图例子,实时显示进度条
不了解Uploadify的,先看看前一篇详细说明 http://www.cnblogs.com/XuebinDing/archive/2012/04/26/2470995.html Uploadify ...
- js实现在页面实时显示时间,一个按钮控制时间暂停和开始
js实现在html实时显示时间,一个按钮控制时间暂停和开始.代码如下: <head><meta charset="UTF-8"><title>& ...
最新文章
- Pandas可视化综合指南:手把手从零教你绘制数据图表
- 只有一流的人才能干出一流的工作,只有具备大量一流的人才的企业才能成为一流的企业...
- Database之SQLSever:SQLSever数据库管理学习并深入理解SQL命令语句进阶综合篇《初级→中级→高级》(持续更新,建议收藏)
- PAT甲级题目翻译+答案 AcWing(链表)
- eclipse 保存html 提示 save could not be completed
- 文件字符输入流的使用 FileReader java
- harmonyOS的架构图,HarmonyOS通用设计基础---应用架构
- 几个 XmlTextReader 的例子, 帮了我大忙.
- 去除DataTable重复数据的三种方法(转)
- 平庸程序员的成长笔记
- graphpad 中文版使用手册
- Tampermonkey油猴脚本安装及入门
- 均线颜色怎么区分_均线入门:一图学会区分不同均线的颜色与炒股技巧
- POJ-2524 Ubiquitous Religions
- python爬虫-抓取内涵吧内涵段子
- 转载一份大佬的面试指南,命中率很高
- 代理模式(静态代理和动态代理)
- c4droid用c语言画爱心,【图片】[自学C语言第五天]发一个作品【c4droid吧】_百度贴吧...
- 群星Stellaris for Mac(太空策略游戏)
- 计算机软件开发工程师简历,net软件工程师的简历范文
热门文章
- 拾遗:『ext4 Quota』
- DataGridView加入CheckBox列 (VB)
- [导入]毕业的大学生的100条忠告
- 如何根据用户IP得到用户所在位置。
- 系统进入低功耗的配置
- 【拔刀吧少年】之shell数组
- c++代码表白_一行 Python 代码能实现什么丧心病狂的功能? | CSDN博文精选
- 怎么确定迭代器后面还有至少两个值_为什么range不是迭代器?range到底是什么类型?
- iphone以旧换新活动_【武商襄阳购物中心】 参与iphone以旧换新活动,最高可抵4300元,旧机可享10%额外补贴...
- 如何实现 OpenAPI 多语言 SDK 开发?