Страницы

Поиск по вопросам

понедельник, 16 декабря 2019 г.

Ожидание в асинхронности

#c_sharp #async_await #tpl


Есть абстрактный пример:

async void Do() 
{
    ...
    await DownloadSomething();
    // какой-то другой код, который выполнится позже 
    ...
}

void FuncMain() 
{
    Do();
    //какой-то код
} 


Когда начинается "долгая"  операция DownloadSomething, управление передаётся в FuncMain,
а после, когда загрузка закончится, продолжается код после DownloadSomething. 
Вопрос: где удерживается await DownloadSomething? Или удерживается в каком-то потоке
из пула? 
    


Ответы

Ответ 1



Смотря, что стоит в DownloadSomething(). Если это IO то поток IO. который фиксирован и независим от приложения. DB, SQL, Download и т.д. в ту же копилку. В момент передачи идут сохрание информации текущей конфигурации потока и как его возвращать. Текущий поток высвобождается и по окончанию происходит обратный вызов из пула нового/исходного потока. (ConfigureAwait(true/false)).

Ответ 2



Чтобы вопрос не оставался без ответа: Дело в том, что async-метод не является методом в обычном понимании этого слова. С точки зрения внешнего кода, его выполнение заканчивается практически сразу (с первым await'ом, который ожидает неокончившийся Task*). На время ожидания метод не выполняется нигде. Это не буддистский коан, а реальная подробность имплементации async/await. По существу await выполняется так: код просто подписывает на окончание выполнения Task'а метод специального скрытого объекта, и завершает выполнение. При окончании работы Task'а метод получает управление, и при помощи довольно простых трюков (наподобие goto в середину кода) возобновляет выполнение кода async-метода. Таким образом, во время await'а метод не выполняется ни в каком потоке. *или tasklike

Комментариев нет:

Отправить комментарий