我有简单的winforms应用程序,我有按钮。点击按钮我正在做这样的事情
private void Button1_Click(object sender, EventArgs e)
{
BackgroundWorker bw_Convert = new BackgroundWorker();
bw_Convert.WorkerReportsProgress = true;
bw_Convert.DoWork += bw_Convert_DoWork;
bw_Convert.RunWorkerCompleted += bw_Convert_RunWorkerCompleted;
bw_Convert.ProgressChanged += bw_Convert_ProgressChanged;
bw_Convert.WorkerReportsProgress = true;
bw_Convert.RunWorkerAsync();
}
我有以下代码用于后台工作程序
public void bw_Convert_DoWork(object sender, DoWorkEventArgs e)
{
for (int i = 0; i <= 1000000; i++)
{
bw_Convert.ReportProgress((100 * (i) / 1000));
}
}
public void bw_Convert_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
progressBarControl1.EditValue = e.ProgressPercentage.ToString();
}
通过这样做。为什么我的主线程在我处理Background Worker中的东西时被绞死。
答案 0 :(得分:2)
因为ReportProgress事件处理程序在主线程上执行:
对ReportProgress方法的调用是异步的并返回 立即。 ProgressChanged事件处理程序在线程上执行 创建了BackgroundWorker。
因此,您不断从后台线程调用ReportProgress
,这会使您的主线程始终忙于处理此事件。
如果你在后台有很多快速的工作要做,那么尝试只报告每次第n次迭代,而不是每次迭代都引发事件:
public void bw_Convert_DoWork(object sender, DoWorkEventArgs e)
{
for (int i = 0; i <= 1000000; i++)
{
if (i % 10000 == 0)
bw_Convert.ReportProgress(i);
// do something
}
}
答案 1 :(得分:1)
在{i}}事件上执行ProgressChanged
事件,以便您可以访问控件
后台工作程序中的代码在很短的时间内执行,导致在很短的时间内引发许多事件,使代码做出反应,好像它会在UI线程上完全执行。
事实上,大部分工作都是在UI线程中完成的,因为更新屏幕上的控件比循环迭代要多得多。