将两个并行任务的结果合并到一个列表中

时间:2014-12-01 12:39:21

标签: c# .net multithreading parallel-processing task-parallel-library

我想在一个List集合中组合2个任务的结果。

确保 - 我想并行运行这两种方法。

代码:

List<Employee> totalEmployees = new List<Employee>();

方法1:

public async Task<IEnumerable<Employee>> SearchEmployeeFromDb();

方法2:

public async Task<IEnumerable<Employee>> GetEmployeeFromService();

现在,我想在totalEmployees字段中保存这两个方法的结果,这两个方法也应该异步运行。

5 个答案:

答案 0 :(得分:19)

虽然很多答案都很接近,但最干净,最有效的选择是使用Task.WhenAll并结合SelectMany

async Task<IEnumerable<Employee>> Combine()
{
    var results = await Task.WhenAll(SearchEmployeeFromDb(), GetEmployeeFromService());
    return results.SelectMany(result => result);
}

这假设并行意味着同时发生。如果您希望从头开始使用多个线程运行这些操作(包括async方法的同步部分),您还需要使用Task.Run将工作卸载到ThreadPool线程:< / p>

private async Task<IEnumerable<Employee>> Combine()
{
    var results =
        await Task.WhenAll(Task.Run(() => SearchEmployeeFromDb()), Task.Run(() => GetEmployeeFromService()));
    return results.SelectMany(result => result);
}

答案 1 :(得分:1)

您可以使用Task.WhenAll创建一个任务,该任务将在所有提供的任务完成后返回

var result = await Task.WhenAll(SearchEmployeeFromDb(),GetEmployeeFromService());
var combined = result[0].Concat(result[1]);

答案 2 :(得分:1)

  • 启动两项任务
  • 使用Task.WhenAll等待两项任务完成
  • 使用Enumerable.Concat合并结果


var searchEmployeesTask = SearchEmployeeFromDb();
var getEmployeesTask = GetEmployeeFromService();

await Task.WhenAll(searchEmployeesTask, getEmployeesTask);

var totalEmployees = searchEmployeesTask.Result.Concat(getEmployeesTask.Result);

答案 3 :(得分:0)

这样的事情应该有效:

var t1 = SearchEmployeeFromDb()
var t2 = GetEmployeeFromService()

await Task.WhenAll(t1, t2)

// Now use t1.Result and t2.Result to get `totalEmployees`

答案 4 :(得分:0)

使用ConfigureAwait(false)来避免死锁,定义任务,执行然后等待。

var fromDbTask = SearchEmployeeFromDb().ConfigureAwait(false);
var fromServiceTask = GetEmployeeFromService().ConfigureAwait(false);

var fromDbResult = await fromDbTask;
var totalEmployees = new List(fromDbResult);

var fromServiceResult = await fromServiceResult;
totalEmployees.AddRange(fromServiceResult);

...或者使用您希望合并两个列表的方式。

我更新了解决方案,创建列表然后附加第一个结果是不必要的。我们等待第一个方法完成,然后创建列表。