在 .NET Framework 的 System.ComponentModel 命名空间中有个 BackgroundWorker 类,这个类提供的功能是在单独的线程中执行异步任务,我们可以使用它来实现一些耗时的、需要在后台执行的一些操作,这个类提供的方法比较浅显易懂,常用方法说明:
事件 ProgressChanged:可用于跟踪任务处理的进度,调用 ReportProgress 方法后会执行;
事件 RunWorkerCompleted:发生在任务结束时,取消、异常都会导致任务结束;
事件 DoWork:要执行的任务事件,调用 RunWorkerAsync 方法后会执行;
属性 WorkerReportsProgress:设置能否报告进度;
属性 WorkerSupportsCancellation:设置能否被取消;
属性 CancellationPending:指示是否收到了取消指令,调用 CancelAsync 方法后此值为 true。
示例程序的准备,在 Form1 窗体上添加文本框 textBox1、开始按钮 button_start、取消按钮 button_cancel,然后参考如下主要的窗体代码:
BackgroundWorker backgroundWorker = new BackgroundWorker();
private void Form1_Load(object sender, EventArgs e)
{
backgroundWorker.ProgressChanged += BackgroundWorker_ProgressChanged;
backgroundWorker.RunWorkerCompleted += BackgroundWorker_RunWorkerCompleted;
backgroundWorker.DoWork += BackgroundWorker_DoWork;
backgroundWorker.WorkerReportsProgress = true;
backgroundWorker.WorkerSupportsCancellation = true;
}
private void BackgroundWorker_DoWork(object sender, DoWorkEventArgs e)
{
int i = 0;
while (i <= 100)
{
if (backgroundWorker.CancellationPending)
{
e.Cancel = true;
return;
}
backgroundWorker.ReportProgress(i);
Thread.Sleep(100);
i += 10;
}
}
private void BackgroundWorker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
if (e.Cancelled)
{
textBox1.AppendText("任务被中止");
}
else
{
textBox1.AppendText("任务已完成");
}
}
private void BackgroundWorker_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
textBox1.AppendText(e.ProgressPercentage + "%" + Environment.NewLine);
}
private void button_start_Click(object sender, EventArgs e)
{
textBox1.Clear();
backgroundWorker.RunWorkerAsync();
}
private void button_cancel_Click(object sender, EventArgs e)
{
backgroundWorker.CancelAsync();
}
DoWorkEventArgs 事件参数属性 Cancel 与 RunWorkerCompletedEventArgs 事件参数属性 Cancelled 具有一致性,利用此值能够得知任务是主动取消的还是正常结束的;取消任务的方法需要自己结合指示状态手动用 return 等方式干预;DoWork 事件中的方法会异步执行,所以不能在此事件中操作 WinForm 界面,应当在报告进度时和任务结束时再操作界面元素。
我们要模拟执行的异步任务是从 0% 数到 100% 并输出过程值和结果值,中间允许手动取消任务,运行结果示例图:

BackgroundWorker 还具有 IsBusy 属性可用来监控任务状态;在执行任务和报告进度时可以带上自定义的参数。
相关环境:.NET Framework、Windows 窗体应用