C#: Async Task: Cancel



我有一个函数在几秒钟内完成一些工作。我想在一段时间后取消这个任务,但是做不到。我的目标是做asyncFunction 5秒,然后,移动到一个不同的任务。由于某种原因,我似乎不能等待_t1。

private async Task asyncFunction(string line_1, string line_2, string line_3, string line_4, int _time, System.Threading.CancellationTokenSource _cts)
{
_cts.Token.ThrowIfCancellationRequested();
await Task.Run(async () => {
someFunction_01(line_1, line_2, line_3, line_4);                
someFunction_01("HELLO WORLD");
await Task.Delay(_time, _cts.Token);
});
}

我调用函数的方式是:

TimeSpan _timeout = TimeSpan.FromSeconds(5);
var timeoutCancellationTokenSource = new System.Threading.CancellationTokenSource(_timeout);

Task _t1 = asyncFunction("LINE 01", " ", " ", " ", 6000, timeoutCancellationTokenSource);
if (await Task.WhenAny(_t1, Task.Delay(_timeout, timeoutCancellationTokenSource.Token)) == _t1)
{                    
await _t1;
}
else
{
// timeout/cancellation logic                    
timeoutCancellationTokenSource.Cancel();
}

我似乎无法取消任务。asyncFunction内部的延迟。任何代码帮助是感激的。

我不太明白这段代码的目的。特别是if语句:

if (await Task.WhenAny(_t1, Task.Delay(_timeout, timeoutCancellationTokenSource.Token)) == _t1)

为什么将_timeout传递给Task.Delay,这与创建timeoutCancellationTokenSource时的超时相同?

如果我们忽略你给Task.Delay的第一个参数,这也意味着你有两个调用Task.Delay与相同的CancellationToken,现在你有一个竞争条件,不可能预测哪个Task.Delay将首先被取消。


要显示如何使取消工作的示例,您可以这样做:

TimeSpan _timeout = TimeSpan.FromSeconds(1);
var timeoutCancellationTokenSource = new System.Threading.CancellationTokenSource(_timeout);
Task _t1 = asyncFunction("LINE 01", " ", " ", " ", 2000, timeoutCancellationTokenSource);
try
{
await _t1;
}
catch (OperationCanceledException)
{
Console.WriteLine("Operation was cancelled");
}
// Output: Operation was cancelled

如果_timeout比传递给asyncFunction2000毫秒长,任务将在2秒后完成而不被取消。

请查看此文件以进行测试运行。

最新更新