【发布时间】:2019-04-24 10:56:53
【问题描述】:
我有几个类似的任务,每个任务都限制为超时,即必须比指定时间更快地完成或返回空结果。这些任务的主要目的是接收来自服务器的具有超时限制的响应。 此类任务的示例如下:
public async Task<List<Data>> GetDataWithTimeoutAsync(InputData data, int timeout)
{
List<Data> resultData = new List<Data>;
await Task.WhenAny(Task.Run(async () =>
{
resultData.Add(SomeWork(data));
}),
Task.Delay(timeout));
return resultData;
}
这些任务中的每一个都可以单独正常工作。
但我想并行运行一些这样的任务。为此,我使用以下代码。
public async Task<List<List<Data>>> GetAllDataAsync()
{
var resultTasks = new ConcurrentBag<Task<List<Data>>>();
var firtsTask = GetDataWithTimeoutAsync(firstInputData, firtsTimeout);
var secondTask = GetDataWithTimeoutAsync(secondInputData, secondTimeout);
var thirdTask = GetDataWithTimeoutAsync(thirdInputData, thirdTimeout);
resultTasks.Add(Task.Run(() => firtsTask));
resultTasks.Add(Task.Run(() => secondTask));
resultTasks.Add(Task.Run(() => thirdTask));
await Task.WhenAll(resultTasks);
var result = resultTasks.Select(t => t.Result).ToList();
return result;
}
但如果为嵌套任务设置了不同的超时时间,此代码将无法正常工作。在这种情况下,所有任务都会在最小的超时后完成。
如果每个任务都是 WhenAny 的结果,我如何与 WhenAll 并行运行一些任务?
【问题讨论】:
-
您不应该在
resultTasks.Add(Task.Run(() => firtsTask));执行Task.Run,因为您已经在GetDataWithTimeoutAsync中启动了一个任务。就做resultTasks.Add(firtsTask)); -
@Peter Bons 我试图这样做。这没有导致结果。
-
@AndreyDengin 甚至没有必要为您创建答案:stackoverflow.com/questions/4238345/…
-
@AndreyDengin 也许可以选择使用
CancellationTokenSource.CancelAfter,如果令牌没有被取消,则进行实际工作......