You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在不同返回类型的异步任务完成时分别处理结果?

处理不同返回类型的异步任务:完成即处理结果

针对不同返回类型的异步任务,要实现并发执行且完成后立即处理结果,有几种简洁的实现方式:

方案一:分别await已启动的任务

先启动所有任务让它们并发运行,之后逐个await每个任务,任务完成后立即处理结果。这种方式代码简单,适合任务数量不多的场景:

private async Task CompleteTasksAsync()
{
    // 先启动所有任务,触发并发执行
    var taskA = GetStringAsync();
    var taskB = GetIntAsync();
    var taskC = GetStringListAsync();
    var taskD = GetGenericAsync<double>(1d);

    // 逐个等待任务完成,完成后立即处理结果
    Console.WriteLine(await taskA);
    Console.WriteLine(await taskB);
    var listResult = await taskC;
    Console.WriteLine($"列表内容:{string.Join(", ", listResult)}");
    Console.WriteLine(await taskD);
}

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);

所有任务在初始化阶段就已并发执行,后续的await只是等待对应任务的结果,若任务已提前完成则直接获取结果处理,不会额外阻塞。

方案二:按任务完成顺序处理(Task.WhenAny循环)

如果需要严格按照任务实际完成的先后顺序处理结果,可使用Task.WhenAny循环监听,每次处理刚完成的任务:

private async Task CompleteTasksAsync()
{
    var tasks = new HashSet<Task>
    {
        GetStringAsync(),
        GetIntAsync(),
        GetStringListAsync(),
        GetGenericAsync<double>(1d)
    };

    while (tasks.Count > 0)
    {
        var completedTask = await Task.WhenAny(tasks);
        tasks.Remove(completedTask);

        // 根据任务类型匹配处理逻辑
        if (completedTask is Task<string> stringTask)
            Console.WriteLine(stringTask.Result);
        else if (completedTask is Task<int> intTask)
            Console.WriteLine(intTask.Result);
        else if (completedTask is Task<List<string>> listTask)
            Console.WriteLine($"列表内容:{string.Join(", ", listTask.Result)}");
        else if (completedTask is Task<double> doubleTask)
            Console.WriteLine(doubleTask.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);

这种方式会持续监控未完成任务,一旦有任务完成就立即处理,完全遵循任务实际完成的先后顺序。

方案三:绑定任务与处理逻辑(通用包装)

通过通用方法将每个任务和对应的处理逻辑绑定,避免后续类型判断,代码更简洁:

private async Task CompleteTasksAsync()
{
    var processingTasks = new List<Task>
    {
        HandleTask(GetStringAsync(), result => Console.WriteLine(result)),
        HandleTask(GetIntAsync(), result => Console.WriteLine(result)),
        HandleTask(GetStringListAsync(), result => Console.WriteLine($"列表内容:{string.Join(", ", result)}")),
        HandleTask(GetGenericAsync<double>(1d), result => Console.WriteLine(result))
    };

    await Task.WhenAll(processingTasks);
}

// 通用包装方法:等待任务完成后执行处理逻辑
private async Task HandleTask<T>(Task<T> task, Action<T> handler)
{
    var result = await task;
    handler(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);

每个任务在完成后会自动触发对应的处理逻辑,最后用Task.WhenAll等待所有处理流程结束即可。

内容的提问来源于stack exchange,提问作者ARH

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.30 23:27:45