英文:
Process async tasks of different result types as they complete
问题
我试图在异步任务完成时/当它们完成时处理每个任务的结果。这些任务具有不同的结果集。我希望并行执行这些任务,但需要在任何任务完成时处理结果。
有很多谷歌搜索结果关于异步函数具有相同的返回类型,但是,我找不到一个具有不同结果集的示例。
private async Task CompleteTasksAsync()
{
var taskA = GetStringAsync();
var taskB = GetIntAsync();
var taskC = GetStringListAsync();
var taskD = GetGenericAsync<double>(1d);
await Task.WhenAll(taskA, taskB, taskC, taskD); // 此语句将等待
// 直到所有任务完成
// 当任务A完成时,打印 taskA.Result
// 当任务B完成时,打印 taskB.Result
// 当任务C完成时,打印 taskC.Result
// 当任务D完成时,打印 taskD.Result
}
private Task<string> GetStringAsync() => Task.FromResult("string");
private Task<int> GetIntAsync() => Task.FromResult(1);
private Task<List<string>> GetStringListAsync()
=> Task.FromResult(new List<string> { "string" });
private Task<T> GetGenericAsync<T>(T data) => Task.FromResult(data);
英文:
I am trying to process each async task result when/as they complete. These tasks have different result sets. I like to execute these tasks concurrently but need to process the result when any finishes.
There are many google search results when async functions have the same return type, however, I couldn't get my hand to one with different result sets.
private async Task CompleteTasksAsync()
{
var taskA = GetStringAsync();
var taskB = GetIntAsync();
var taskC = GetStringListAsync();
var taskD = GetGenericAsync<double>(1d);
//var tasks = new[] {taskA, taskB, taskC, taskD} // this will only work if all
// tasks have same return type
await Task.WhenAll(taskA, taskB, taskC, taskD); // This statement will wait
// until all tasks are completed
// when Task A finished Console.WriteLine(taskA.Result);
// when Task B finished Console.WriteLine(taskB.Result);
// when Task C finished Console.WriteLine(taskC.Result);
// when Task D finished Console.WriteLine(taskD.Result);
}
private Task<string> GetStringAsync() => Task.FromResult("string");
private Task<int> GetIntAsync() => Task.FromResult(1);
private Task<List<string>> GetStringListAsync()
=> Task.FromResult(new List<string> { "string"});
private Task<T> GetGenericAsync<T>(T data) => Task.FromResult(data);
答案1
得分: 1
简单的答案是编写更多的异步方法;
public async Task ProcessString(){
var str = await GetStringAsync();
DoSomething(str);
}
await Task.WhenAll(
ProcessString(),
ProcessInt(),
...
);
英文:
The simple answer is to write more async methods;
public async Task ProcessString(){
var str = await GetStringAsync();
DoSomething(str);
}
await Task.WhenAll(
ProcessString(),
ProcessInt(),
...
);
答案2
得分: 0
最后,对于那些不想使用if/switch
的人。我使用了Dictionary<TAsk, Action>
帮助我管理任务和结果。
private async Task CompleteTasksAsync()
{
var taskA = GetStringAsync();
var taskB = GetIntAsync();
var taskC = GetStringListAsync();
var taskD = GetGenericAsync<double>(1d);
Dictionary<Task, Action> tasks = new()
{
{taskA, () => Console.WriteLine(taskA.Result)},
{taskB, () => Console.WriteLine(taskB.Result)},
{taskC, () => Console.WriteLine(taskC.Result)},
{taskD, () => Console.WriteLine(taskD.Result)}
};
while (tasks.Any())
{
var completedTask = await Task.WhenAny(tasks.Keys);
tasks[completedTask]();
tasks.Remove(completedTask);
}
}
英文:
Finally, For anyone who want to do it without the if/switch
. I used Dictionary<TAsk, Action>
and this helped me to shape the tasks and results.
private async Task CompleteTasksAsync()
{
var taskA = GetStringAsync();
var taskB = GetIntAsync();
var taskC = GetStringListAsync();
var taskD = GetGenericAsync<double>(1d);
Dictionary<Task, Action> tasks = new()
{
{taskA, () => Console.WriteLine(taskA.Result)},
{taskB, () => Console.WriteLine(taskB.Result) }, {taskC, () => Console.WriteLine(taskC.Result) },
{taskD, () => Console.WriteLine(taskD.Result) }
};
while (tasks.Any())
{
var completedTask = await Task.WhenAny(tasks.Keys);
tasks[completedTask]();
tasks.Remove(completedTask);
}
}
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论