我有几个类似的任务,每个任务都有一个超时时间,即必须比指定时间快完成或返回空结果。这些任务的主要目的是从服务器接收具有超时限制的响应。 此类任务的示例如下:
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并行运行一些任务?
答案 0 :(得分:0)
您的代码无法编译,所以我写了类似的东西。我无法复制您的结果。就我而言,具有不同超时的WhenAll
可以正常工作。当最长的任务完成时,即第二个任务(200毫秒)完成时,它就会完成。
public static async Task Main(string[] args)
{
var task1 = GetDataAsync(100).WithTimeout(50); // Should timeout after 50 msec
var task2 = GetDataAsync(200).WithTimeout(300); // Should complete after 200 msec
var task3 = GetDataAsync(300).WithTimeout(100); // Should timeout after 100 msec
var stopwatch = Stopwatch.StartNew();
var results = await Task.WhenAll(task1, task2, task3); // Wait for all
stopwatch.Stop();
Console.WriteLine($"Results: {String.Join(", ", results)}");
Console.WriteLine($"Elapsed: {stopwatch.ElapsedMilliseconds} msec");
}
private static async Task<int> GetDataAsync(int input) // the input is used as delay
{
await Task.Delay(input);
return input;
}
public static Task<T> WithTimeout<T>(this Task<T> task, int timeout)
{
var delayTask = Task.Delay(timeout).ContinueWith(_ => default(T),
TaskContinuationOptions.ExecuteSynchronously);
return Task.WhenAny(task, delayTask).Unwrap();
}
输出:
Results: 0, 200, 0
Elapsed: 211 msec