2015-10-16 50 views
0

我想弄清楚如何在我的应用程序的数据层中正确使用async/await来并行执行多个数据库调用。运行多个Linq查询异步

我正在使用Entity Framework和Linq来完成我的数据调用。

可以从任何应用程序类型(MVC Web App,Web API项目,Win From,Windows Service等)调用数据层 - 因此该方法的结果应该是单个对象。

public static async void GetLedger(long id, DateTime StartDate, DateTime EndDate) 
    { 
     var task_1 = DoComplexDBCallAsync1(); 
     var task_2 = DoComplexDBCallAsync2(); 
     var task_3 = DoComplexDBCallAsync3(); 
     var task_4 = DoComplexDBCallAsync4(); 
     var task_5 = DoComplexDBCallAsync5(); 

     await Task.WhenAll(task_1, task_2, task_3, task_4, task_5); 

     var result = ProcessAndMergeResultsFromAllDBCalls(task_1.Result, task_2.Result, task_3.Result, task_4.Result, task_5.Result); 

     return result; 
    } 

    private static async Task<List<SomeComplexType>> DoComplexDBCallAsync1(long id) 
    { 
     using (var metadata = DataAccess.getDesktopMetadata()) 
     { 
      var accounts = await (from row in metadata.db_GLAccount 
            where row.busID == id 
            select row).ToListAsync(); 

      return accounts; 
     } 
    } 

我将如何改变上述返回的Task<>object呢?

我是否需要用另一种方法来包装它,该方法通过Task运行或RunSynchronously()调用GetLedger异步方法并返回结果? 如果是的话代码将如何看,有什么我需要知道的?

这种情况下的最佳做法是什么?

+2

答案是**你不**。它应该返回一个'Task',而不是'void'或返回一个实际的项目。这就是使它能够异步正常工作的原因。如果您希望它同步运行,那么只需使用同步EF代码完全创建一个完全同步的方法。 – Servy

+0

不需要。他们需要自己异步,并能够看到这种方法是异步的。使用'await'使得实现异步更容易,但它仍然需要在那里。 – Servy

回答

-1

你会使用等候如下

public static async Task<SomeObject> GetLedger(long id, DateTime StartDate, DateTime EndDate) 
    { 
     var task_1 = DoComplexDBCallAsync1(); 
     var task_2 = DoComplexDBCallAsync2(); 
     var task_3 = DoComplexDBCallAsync3(); 
     var task_4 = DoComplexDBCallAsync4(); 
     var task_5 = DoComplexDBCallAsync5(); 

     var result = ProcessAndMergeResultsFromAllDBCalls(await task_1, await task_2, await task_3, await task_4, await task_5); 

     return result; 
    } 

在“等待”关键字将自动获得任务的结果,并将其应用到变量时,DB调用返回。 MSDN

你会再调用

var result = await GetLedger(id, StartDate, EndDate); 

一切都完成后,这将继续。

+0

您已经将所有5个数据库操作并行执行的操作从一个顺序改为全部操作,并且有迹象表明它们应该并行执行。他还特别询问了如何使用这种方法*而不是*返回一个“任务”。 – Servy

+0

哎呀,对不起。我等待在错误的地方。编辑。 – Vlad274