我们得到了一个长时间运行的作业,它需要一个作业详细信息列表并且不共享任何状态,试图在 WPF MVVM .Net 4 项目中运行。看来任务并行库将是最佳选择,因为它在后台线程上运行并允许并行处理。我创建了一个原型(prototype)应用程序,它也将 MVVM-Light 用于 RelayCommands。示例“aTplTest.7z”位于 https://skydrive.live.com/redir?resid=DA3E430C1A5F3B81!186&authkey=!AOOWYGbB_PToC5A
原型(prototype)主要工作(只是运行斐波那契计算进行测试),除了以下内容。
(例如,如果用户按下 View 关闭窗口按钮,catch 的 Invoke 方法会创建另一个异常。)
private bool CreateVouchers(int[] workList)
{
var loopOptions = new ParallelOptions();
loopOptions.CancellationToken = TokenSource.Token;
var success = false;
try
{
Parallel.ForEach(workList, loopOptions, t => BuildVoucher(t));
success = true;
}
catch (OperationCanceledException)
{
var scm = new Action(ShowCancellationMessage);
Application.Current.Dispatcher.Invoke(DispatcherPriority.Normal, scm);
}
return success;
}
我将使用任何解决方案更新这篇文章和源示例。
最佳答案
要自动启动长时间运行的进程,只需将以下 Window_Loaded 处理程序添加到您定义 Window_Closing 处理程序的代码隐藏中:
private void Window_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{
var viewModel = (VoucherBuilderViewModel)this.DataContext;
viewModel.CancelCommand.Execute(null);
}
private void Window_Loaded(object sender, RoutedEventArgs e)
{
var viewModel = (VoucherBuilderViewModel)this.DataContext;
viewModel.RunJob();
}
当然,不要忘记在 XAML 中注册事件处理程序:
<Window Closing="Window_Closing" Loaded="Window_Loaded">
并且要在关闭窗口时摆脱异常,只需添加以下空检查:
catch (OperationCanceledException)
{
if (Application.Current != null)
{
var scm = new Action(ShowCancellationMessage);
Application.Current.Dispatcher.Invoke(DispatcherPriority.Normal, scm);
}
}
关于.net - TPL WPF MVVM 如何使其工作?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13005755/