我是一个像其他人一样懒散的开发人员:)为什么我尝试编写一个静态方法来使用BackgroundWorker。这种方法就是吹嘘:
public static void RunInThread( DoWorkEventHandler method
,ProgressChangedEventHandler progressHandler
,RunWorkerCompletedEventHandler completed)
{
var bkw = new BackgroundWorker();
bkw.DoWork += method;
bkw.ProgressChanged += progressHandler;
bkw.RunWorkerCompleted += completed;
bkw.WorkerReportsProgress = true;
bkw.RunWorkerAsync();
}
但是我有一个使用BackgroundWorker.ReportProgress方法的问题。 这里有谁可以帮助我吗? tnx
答案 0 :(得分:0)
如果不是从void
返回RunInThread
而是返回BackgroundWorker
类(bkw)的对象,然后在DoWork
中使用该实例调用{{1} }}
答案 1 :(得分:0)
虽然Haris的解决方案是可接受的“快速解决方案”,但您的静态方法存在一个主要的设计缺陷;作为BackgroundWorker
的Component
类实现IDisposable
,因此应该在其生命的最后处置。
重新创建模式的最佳方法是在另一个线程上手动调用您的工作函数。唯一的缺点是,当您更新进度时,必须调用Dispatcher.Invoke
才能与UI线程上的任何内容进行交互。以下是您如何做到这一点的示例。
using System.Threading;
public static void RunInThread<TProgress>(
Action<Action<TProgress>> worker,
Action<TProgress> updateProgress,
Action workerCompleted)
{
Thread workerThread = new Thread(() =>
{
worker(updateProgress);
workerCompleted();
});
workerThread.Start();
}
因为它是一种通用方法,您可以使用它来报告您喜欢的任何类型的进度。以下是您可以调用它的示例:
RunInThread<double>(
updateProgress =>
{
Thread.Sleep(500);
updateProgress(0.5);
Thread.Sleep(500);
updateProgress(1);
},
progress =>
{
this.Dispatcher.Invoke(() =>
{
progressLabel.Text = progress.ToString();
});
},
() =>
{
this.Dispatcher.Invoke(() =>
{
progressLabel.Text = "Finished!";
});
}
);
您还可以非常轻松地自定义此方法,以创建在使用单个参数或返回值时更轻松的重载。
public static void RunInThread<TProgress, TParameter>(
Action<Action<TProgress>, TParameter> worker,
Action<TProgress> updateProgress,
Action workerCompleted,
TParameter parameter)
{
Thread workerThread = new Thread(() =>
{
worker(updateProgress, parameter);
workerCompleted();
});
workerThread.Start();
}
public static void RunInThread<TProgress, TResult>(
Func<Action<TProgress>, TResult> worker,
Action<TProgress> updateProgress,
Action<TResult> workerCompleted)
{
Thread workerThread = new Thread(() =>
{
TResult result = worker(updateProgress);
workerCompleted(result);
});
workerThread.Start();
}
public static void RunInThread<TProgress, TParameter, TResult>(
Func<Action<TProgress>, TParameter, TResult> worker,
Action<TProgress> updateProgress,
Action<TResult> workerCompleted,
TParameter parameter)
{
Thread workerThread = new Thread(() =>
{
TResult result = worker(updateProgress, parameter);
workerCompleted(result);
});
workerThread.Start();
}
我还建议您添加一些错误处理代码,以防万一在您的工作职能中出现任何问题,但我会将此练习留给您。