我是一个对.NET中TPL不熟悉的新手。我想了解令牌(CancellationToken
)以及如何使用它来取消执行的任务。下面的代码只传输了一个被取消的任务,而同样的令牌被传递给了两个任务。我的假设是,如果第一个任务超时并且执行了 ctx.Cancel()
,那么为什么我只看到一个异常,而不是两个任务都被取消了?我错过了什么,如何确保两个任务都被取消并且不会占用内存资源。
static void Main(string[] args)
{
Console.WriteLine("Starting application");
var ctx = new CancellationTokenSource();
var token = ctx.Token;
try
{
var task1 = new Program().Run("task1", token);
var task2 = new Program().Run("task2", token);
if (!task1.Wait(1000))
ctx.Cancel();
task2.Wait();
}
catch (AggregateException ex)
{
Console.WriteLine("Aggregate Exception occurred");
foreach (var e in ex.InnerExceptions)
{
Console.WriteLine(e.Message);
}
}
catch (Exception e)
{
Console.WriteLine($"Main Exception: {e.Message}");
}
finally
{
Console.WriteLine("Finish Application");
ctx.Dispose();
}
}
private async Task Run(string name, CancellationToken token)
{
while(true)
{
if (token.IsCancellationRequested)
{
Console.WriteLine("Task Cancelled");
token.ThrowIfCancellationRequested();
}
Console.WriteLine($"Executing {name} ...");
await Task.Delay(250, token);
}
}
只有一个异常被抛出,其他任务发生了什么?此外,
Console.WriteLine("Task Cancelled")
从未执行。输出:
Starting application
Executing task1 ...
Executing task2 ...
Executing task2 ...
Executing task1 ...
Executing task1 ...
Executing task2 ...
Executing task2 ...
Executing task1 ...
Aggregate Exception occurred
A task was canceled.
Finish Application