C#多线程如何刷新主界面?

qufo 2008-06-14 12:11:25
有如下一个线程类,大部分消耗时间的事情都在这个类中写了。
类名 MoreTime,其中就一个浪费时间的东西。
这是一个独立的文件MoreTime.cs


namespace ThreadTest
{
public class MoreTime
{
public void WaitMoreTime()
{
for (int i ; i<500;i++)
{
DoSomething()
Thread.sleep(5000)
}
}
}
}


现在,我想在主界面中,把其中的WaitMoreTime 里的 i 值传回UI线程,我要在一个 LixtBox中显示他们。

下面是启动线程的代码: 在 Form1.cs 中。


namespace ThreadTest
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}

private void button1_Click(object sender, EventArgs e)
{
MoreTime mt = new MoreTime();
ThreadStart start = new ThreadStart(mt.WaitMoreTime);
Thread thread = new Thread(start);
thread.Start();
}
}
}



可是,要怎样改才能让多线程 thread 的WaitMoreTime里的i值能传回到主界面中,并显示在一个 ListBox 中呢?

...全文
6939 24 打赏 收藏 转发到动态 举报
写回复
用AI写文章
24 条回复
切换为时间正序
请发表友善的回复…
发表回复
封尘印 2011-09-16
  • 打赏
  • 举报
回复
mark
xiangbing37 2011-09-02
  • 打赏
  • 举报
回复
mark, too
ziseliuxingzh 2010-11-09
  • 打赏
  • 举报
回复
学习。。。。。。。
accbin 2010-04-16
  • 打赏
  • 举报
回复
mark
hbs_biscuit 2009-02-11
  • 打赏
  • 举报
回复
mark
colorslife 2008-06-21
  • 打赏
  • 举报
回复
呵呵,俺对那些言必称"架构,框架,模式"之类的所谓的高手一向很反感,所以有此签名.
程序员当然首先应该把代码写好,在写好代码的基础上再去钻研模式,架构之类的东西,
没有打下坚实的代码基础,谈这些"模式,架构"什么的也是空谈.
qufo 2008-06-20
  • 打赏
  • 举报
回复
感谢



colorslife


另对你的签名深有同感。
moshuchao 2008-06-16
  • 打赏
  • 举报
回复
Mark
onthebox 2008-06-16
  • 打赏
  • 举报
回复
mark真的很有用
昨天就被以前mark的救了
parfum 2008-06-15
  • 打赏
  • 举报
回复
用委托进行异步调用

//WinForm异步回调
http://topic.csdn.net/u/20080220/00/cc8827e7-cc28-4124-9a40-04a5f35fae50.html
marvelstack 2008-06-15
  • 打赏
  • 举报
回复
看这里的文章解决问题,并知道原理,
通过多线程为基于 .NET 的应用程序实现响应迅速的用户
http://www.microsoft.com/china/MSDN/library/enterprisedevelopment/softwaredev/misMultithreading.mspx
为Windows应用创建简单的异步调用模式
http://www.microsoft.com/china/MSDN/library/architecture/AsynCallPattern.mspx
qufo 2008-06-14
  • 打赏
  • 举报
回复
感谢 colorslife ,已看过文章。
这篇文章中的启动线程是通过一个按钮。

// This event handler creates a thread that calls a
// Windows Forms control in a thread-safe way.
private void setTextSafeBtn_Click(
object sender,
EventArgs e)
{
this.demoThread =
new Thread(new ThreadStart(this.ThreadProcSafe));

this.demoThread.Start();
}

线程的执行体是 this.ThreadProcSafe 也就是说,这个线程的执行体是在跟窗口同一份cs文件中。
下面是关于 ThreadProcSafe的。

// This method is executed on the worker thread and makes
// a thread-safe call on the TextBox control.
private void ThreadProcSafe()
{
this.SetText("This text was set safely.");
}

// This method demonstrates a pattern for making thread-safe
// calls on a Windows Forms control.
//
// If the calling thread is different from the thread that
// created the TextBox control, this method creates a
// SetTextCallback and calls itself asynchronously using the
// Invoke method.
//
// If the calling thread is the same as the thread that created
// the TextBox control, the Text property is set directly.

private void SetText(string text)
{
// InvokeRequired required compares the thread ID of the
// calling thread to the thread ID of the creating thread.
// If these threads are different, it returns true.
if (this.textBox1.InvokeRequired)
{
SetTextCallback d = new SetTextCallback(SetText);
this.Invoke(d, new object[] { text });
}
else
{
this.textBox1.Text = text;
}
}


示例的是在同一个.cs文件中,可以自由使用this.textbox1 可是我的线程类在另外的.cs中。在MoreTime.cs中,怎么访问到Form1中的ListBox呢?


希望有份完整的代码让我学习一下。
colorslife 2008-06-14
  • 打赏
  • 举报
回复
看看这篇文章,讲得很详细的
http://msdn.microsoft.com/zh-cn/library/ms171728(en-us,VS.80).aspx
hyblusea 2008-06-14
  • 打赏
  • 举报
回复
帮顶..顺便学习...
virusswb 2008-06-14
  • 打赏
  • 举报
回复
多线程,异步通信,委托,线程安全
微软有一个例子啊
colorslife 2008-06-14
  • 打赏
  • 举报
回复
独立的文件MoreTime.cs
namespace ThreadTest
{
public class MoreTime
{
public delegate void InvokeOtherThead(int i);

public InvokeOtherThead MainThread;

public void WaitMoreTime()
{

for (int i= 0 ; i<20;i++)
{
Thread.Sleep(2000);

MainThread(i);
}
}
}
}


启动线程的代码:

namespace ThreadTest
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}

private void button1_Click(object sender, EventArgs e)
{
MoreTime mt = new MoreTime();
mt.MainThread = new MoreTime.InvokeOtherThead(AddToList);

ThreadStart start = new ThreadStart(mt.WaitMoreTime);
Thread thread = new Thread(start);
thread.Start();
}

public void AddToList(int i)
{
if (this.listBox1.InvokeRequired)
{
MoreTime mt = new MoreTime();
mt.MainThread = new MoreTime.InvokeOtherThead(AddToList);

this.Invoke(mt.MainThread, new object[] { i});

}
else
{
listBox1.Items.Add(i.ToString());
}
}
}
}


呵呵,在VS2005上测试通过的,楼主结贴吧!
slicelee 2008-06-14
  • 打赏
  • 举报
回复

//跨线程调用
delegate void deleSetText(ListBox l, int i); //定义委托
private void SetText(ListBox l, int i) //一会线程中调这个方法,传入你要显示数据的listbox和要显示的i
{
if (l.InvokeRequired) //判断是否需要跨线程调用
{
Delegate d = new deleSetText(SetText); //第一次进入该方法一般肯定需要,
l.Invoke(d, new object[] { l, i });
}
else
{
listBox1.Items.Add(i.ToString()); //invoke后在用这个方法时不需跨线程了就执行这里了。
}
}

注意else里面的代码一定要是能瞬间完成的哈,这里可是主线程在执行了,再放那种耗时间的要吧界面锁死的。
qufo 2008-06-14
  • 打赏
  • 举报
回复
还是不太明白能给个示例吗?
fuadam 2008-06-14
  • 打赏
  • 举报
回复
设置Control.CheckForIllegalCrossThreadCalls = false;这个属性

然后在你的线程回调函数中就可以把线程的值赋给winform上的控件了
Bullatus 2008-06-14
  • 打赏
  • 举报
回复
委托的方法感觉比Timer的方法好多了。
加载更多回复(4)

110,572

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧