2016-04-28 4 views
1

У меня есть код, который выглядит примерно так:Run множественные ждут одновременно

firstList = await GetFirstListFilesAsync(); 
textBlock1.Text = "found " + firstList.Count + " first list's results"; 
secondList = await GetSecondListFilesAsync(); 
textBlock2.Text = "found " + secondList.Count + " second list's results"; 
thirdList = await GetThirdListFilesAsync(); 
textBlock3.Text = "found " + thirdList.Count + " third list's results" 

Так что теперь он получает первый список, устанавливает первый TextBlock текст, то он получает второй список, устанавливает вторые TextBlock текст и затем получает третий список и устанавливает третий текст TextBlock. Но я бы хотел, чтобы все ожидания выполнялись одновременно, поэтому все TextBlock s будут обновляться более или менее одновременно. Или, может быть, не в одно и то же время - каждый TextBlock будет обновляться по мере завершения соответствующего метода ожидания. Во всяком случае, то, чего я хочу достичь здесь, заключается в том, чтобы быстрее получать результаты. если я запускаю эти методы один за другим, они ждут, пока предыдущий не будет закончен, но если они будут запускать все одновременно, третий метод вернет результат быстрее, не так ли? Так что мой вопрос - это возможно? И если да, то как?

+0

Сделать новую функцию и поставить всю логику GetFirstListFilesAsync, GetSecondListFilesAsync, GetThirdListFilesAsync и возврат массив или словарь int и List <> и запускать эту функцию с ожиданием. – progrAmmar

ответ

4

Я думаю, что это то, что вы ищете:

var tasks = new Task<MyMethodReturnObject>[3]; 
tasks[0] = GetFirstListFilesAsync(); 
tasks[1] = GetSecondListFilesAsync(); 
tasks[2] = GetThirdListFilesAsync(); 

// At this point, all three tasks are running at the same time. 

// Now, we await them all. 
await Task.WhenAll(tasks); 

// Get an individual result, where result is MyMethodReturnObject 
var myText = tasks[0].Result; 

// Loop through results 
var results = tasks.Select(o => o.Result).ToList(); 
foreach (var result in results) 
{ 
    Console.Write(result); 
} 

Источник: http://blog.stephencleary.com/2012/02/async-and-await.html

+0

Хорошо, но как я могу присвоить результаты спискам, используя это? – dace

+0

Моим синтаксисом может быть немного отсюда, поскольку у меня нет доступа к VS прямо сейчас, но что-то вроде: 'code' var results = tasks.Select (o => o.Result) .ToList(); foreach (var result in results) { // Делать что-то с результатом - result.Count; } 'code' – jondow

+0

Очень хороший ответ @jondow. @dace просто выполняет 'firstList = tasks [0] .Result;' – Stamos

1

Вы можете попробовать и сместить произведение в коллекцию Task s и использовать Task.WaitAll для присоединения к темам.

+0

Или так же просто, как поместить все ожидания вместе, вызовите заданное текстовое значение следующим образом: firstList = ожидание GetFirstListFilesAsync(); secondList = ожидание GetSecondListFilesAsync(); thirdList = ждет GetThirdListFilesAsync(); textBlock1.Text = "found" + firstList.Count + "результаты первого списка"; textBlock2.Text = "found" + secondList.Count + "результаты второго списка"; textBlock3.Text = "found" + thirdList.Count + "результаты третьего списка" –

1

ответ Использовать Давида или же просто, как положить все ожидания вместе, то вызовите текстовое уставку так:

firstList = await GetFirstListFilesAsync(); 
secondList = await GetSecondListFilesAsync(); 
thirdList = await GetThirdListFilesAsync(); 

textBlock1.Text = "found " + firstList.Count + " first list's results"; 

textBlock2.Text = "found " + secondList.Count + " second list's results"; 

textBlock3.Text = "found " + thirdList.Count + " third list's results" 
+0

Это все еще не выполняет задачи параллельно. 'GetSecondListFilesAsync' не будет вызываться до тех пор, пока не будет завершено создание' GetFirstListFilesAsync'. –

-1

Просто создайте ваших ожиданий с фактического await на них:

var firstWait = GetFirstListFilesAsync(); 
var secondWait = GetSecondListFilesAsync(); 
var thirdWait = GetThirdListFilesAsync(); 
firstList = await firstWait; 
textBlock1.Text = "found " + firstList.Count + " first list's results"; 
secondList = await secondWait ; 
textBlock2.Text = "found " + secondList.Count + " second list's results"; 
thirdList = await thirdWait ; 
textBlock3.Text = "found " + thirdList.Count + " third list's results"; 

Это еще не покажет никаких результатов, пока первый элемент не завершен, но позволяет добиться прогресса параллельно. Это сложнее, если вы хотите иметь дело с каждым из как, он завершается внутри одной функции, так как тогда вы должны сделать WaitAny в коллекции awaitables, а затем определить (вручную), который (а) был завершен, удалить из сбор и цикл до тех пор, пока все не закончится.

0

Таким образом, вы не хотите группировать блоки await, вы хотите указать, что произойдет, когда они завершатся.

GetFirstListFilesAsync().ContinueWith(task => { 
    textBlock1.Text = "found " + task.Result.Count + " first list's results"; 
}); 
GetSecondListFilesAsync().ContinueWith(task => { 
    textBlock2.Text = "found " + task.Result.Count + " second list's results"; 
}); 
GetThirdListFilesAsync().ContinueWith(task => { 
    textBlock3.Text = "found " + task.Result.Count + " third list's results"; 
}); 

Этот путь будет самый быстрый способ сделать это, потому что, как только Task завершается, ваш textBlock.Text будет установлен, и они не будут ждать на предыдущий, чтобы закончить.

0

Я бы хотел, чтобы все ожидания выполнялись одновременно, поэтому все текстовые блоки будут обновляться более или менее одновременно. Или, может быть, не в одно и то же время - каждый TextBlock будет обновляться по мере завершения соответствующего метода ожидания.

Затем определяют несколько новых методов:

private async Task<TFirst> GetFirstListFilesAndDisplayAsync() 
{ 
    var firstList = await GetFirstListFilesAsync(); 
    textBlock1.Text = "found " + firstList.Count + " first list's results"; 
} 

private async Task<TSecond> GetSecondListFilesAndDisplayAsync() 
{ 
    var secondList = await GetSecondListFilesAsync(); 
    textBlock2.Text = "found " + secondList.Count + " second list's results"; 
} 

private async Task<TThird> GetThirdListFilesAndDisplayAsync() 
{ 
    var thirdList = await GetThirdListFilesAsync(); 
    textBlock3.Text = "found " + thirdList.Count + " third list's results"; 
} 

, а затем вызвать их все одновременно:

var firstTask = GetFirstListFilesAndDisplayAsync(); 
var secondTask = GetSecondListFilesAndDisplayAsync(); 
var thirdTask = GetThirdListFilesAndDisplayAsync(); 

await Task.WhenAll(firstTask, secondTask, thirdTask); 

firstList = await firstTask; 
secondList = await secondTask; 
thirdList = await thirdTask;