2013-05-02 3 views
5

У меня есть List из Task<bool>, что я хочу, чтобы перебирать его и в зависимости от ожидаемого результата я решить, следует ли продолжать или сломаться, но иронически foreach просто выполняет поставленные задачи и ждут ключевое слово не работаетAwait Внутри Foreach Ключевое слово

Вот мой код

private async void Execute(object sender, EventArgs e) 
{ 
    var tList = new List<Task<bool>> { Method1(), Method2()}; 

    foreach (var task in tList) 
    { 
     var result = await task; 

     if(!result) 
      break; 
    } 
} 

public async Task<bool> Method1() 
{ 
    await Task.Delay(1000); 
    Console.WriteLine("Method1"); 
    return false; 
} 

public async Task<bool> Method2() 
{ 
    await Task.Delay(1000); 
    Console.WriteLine("Method2"); 
    return true; 
} 

Результат: Обе функции выполняют.

Вопрос: Как я могу воспользоваться ожиданием внутри foreach?.

И спасибо заблаговременно.

+0

'Method1()' возвращает 'true', поэтому я ожидаю, что ваш цикл будет продолжен. Тем не менее, у вас есть фундаментальная проблема: вы начинаете обе задачи до начала цикла, поэтому даже если первая задача вернула «false», возможно, что вторая задача уже завершена. Вы по-прежнему будете игнорировать дальнейшие * результаты *, но вы не будете обязательно пропускать вычисление этих результатов. – dlev

+0

извините ** отредактировал его ** с тем же результатом, и он должен сломаться, если возвращается false. –

ответ

9

Вы можете использовать await в пределах foreach точно так же, как сейчас.

Результат: Обе функции выполнены.

Обе функции следует выполнить. Значение result не установлено в значение false до тех пор, пока не вернется Method2, после чего оба из них уже запущены. Вы также запускаете как Task<bool> экземпляры, так и перед вами await, так что оба (потенциально) работают до вашего цикла foreach.

Обратный порядок ваших методов, и они не будут как обязательно перспективе (хотя они могут, как и вы начинаете их):

var tList = new List<Task<bool>> { Method2(), Method1()}; 

Если вы хотите задержать это полностью, мог бы написать его как:

var tList = new List<Func<Task<bool>>> { Method2, Method1}; 

foreach (var taskFunc in tList) 
{ 
    var result = await taskFunc(); 

    if(!result) 
     break; 
} 
+2

Как я упоминал в своем комментарии к вопросу, просто потому, что вы не «ждете», какая-то конкретная задача не означает, что он не будет * запускать *. Проблема заключается в том, что методы запускаются до цикла, поэтому ожидаемые или нет, они оба завершатся в какой-то момент (так как явно не происходит аннулирования.) – dlev

+0

@dlev Very true ... –

+0

см. Редактирование сообщения с тот же Результат. то, что я хочу, произойдет, если первый метод возвращает false, не выполняет второй ... –

Смежные вопросы