处理已取消任务中抛出的异常

时间:2013-10-24 02:34:36

标签: c# task-parallel-library

我正在处理Exam Ref 70-483: Programming in C#一书中的示例,并且遇到了列表1-44中以下代码的问题。在此示例中,作者试图证明延续任务可以访问在先行任务中抛出的未处理异常,并且可以在适当的情况下处理它们。

static void Main(string[] args)
{
    CancellationTokenSource cancellationTokenSource = new CancellationTokenSource();
    CancellationToken token = cancellationTokenSource.Token;

    Task task = Task.Run(() =>
    {
        while (!token.IsCancellationRequested)
        {
            Console.Write("*");
            Thread.Sleep(1000);
        }
        throw new OperationCanceledException();
    }, token).ContinueWith((t) =>
    {
        t.Exception.Handle((e) => true);
        Console.WriteLine("You have canceled the task.");
    }, TaskContinuationOptions.OnlyOnCanceled);

    Console.WriteLine("Press enter to stop the task.");
    Console.ReadLine();

    cancellationTokenSource.Cancel();
    task.Wait();

    Console.WriteLine("Press enter to end the application.");
    Console.ReadLine();
}

不幸的是,这行代码在延续

t.Exception.Handle((e) => true);

引发异常,因为t.Exceptionnull

在该行设置断点,我可以看到t.StatusCanceled,而不是Faulted。这是为什么没有例外吗?处理先行任务中引发的异常的正确方法是什么?

2 个答案:

答案 0 :(得分:1)

使用

task.ContinueWith(HandleError, TaskContinuationOptions.OnlyOnFaulted);

取消的任务并不例外......因此不会包含例外情况。有故障的人会。

答案 1 :(得分:0)

将清单1-44的代码更改为:

Task task = Task.Run(() => { 
    while (true) 
    {
     token.ThrowIfCancellationRequested();
     Console.Write("*");
     Thread.Sleep(1000); }
    }, token).ContinueWith(t =>
 { Console.WriteLine("You have canceled the task"); }, TaskContinuationOptions.OnlyOnCanceled);