Я связываюсь со всей функциональностью async / await в C# прямо сейчас.
Думаю, я знаю, для чего это нужно. Но я сталкивался с местами, где я не хочу, чтобы общее наследование всех методов, вызывающих мою библиотечную функцию, было "асинхронным".
Подумайте об этом (грубый псевдокод, на самом деле не представляющий реальную вещь, это просто о контексте):
string JokeOfTheHour;
public string GiveJokeOfTheHour()
{
if (HourIsOver)
{
jokeOfTheHour = thirdPartyLibrary.GetNewJoke().GetAwaiter().GetResult();
}
return jokeOfTheHour;
}
Я бы назвал здесь следующие причины:
Теперь я хочу знать, какие есть общие правила для этого. Но, к сожалению, я не могу найти простых утверждений или правил в Интернете, где кто-нибудь сказал бы: «В этой, этой и этой ситуации вы можете остановить это ключевое слово« async », всплывающее в вашем дереве вызовов методов». Я только что видел, как люди (некоторые из них Microsoft MVP) говорили о том, что существуют ситуации, в которых это должно быть сделано, а также заявляли, что вы должны использовать .GetAwaiter (). GetResult () в качестве лучшей практики, но они никогда не конкретно о самих ситуациях.
Я ищу простое общее правило, в котором я могу сказать:
Несмотря на то, что я могу вызывать сторонние функции, которые являются асинхронными, я не выполняю async и не хочу отображаться как таковые. Я работаю на нижнем уровне и использую кеши 99,99999% времени. Мне не нужно, чтобы мой пользователь реализовал методологию async полностью до того места, где моему фактическому пользователю нужно решить, где останавливается выполнение async (что заставляет моего пользователя, который действительно должен своевременно извлекать выгоду из моей библиотеки, писать больше кода и выполнять больше время).
Буду очень благодарен за вашу помощь :)
«Разделение озабоченности». - Тогда почему бы не довести его до максимума и разделить геттер и (асинхронный) апдейтер?
Спасибо за эту идею. Это действительно хорошо.
Я поддерживаю предложение @Fildor. И я также хочу упомянуть, что с вашей текущей структурой GetNewJoke будет вызываться более одного раза, если вы не используете механизм блокировки. А использование блокировки создает в вашем случае большое узкое место. Так что это еще одна причина, чтобы согласиться с предложением Филдора.
Как автор библиотеки, вы В самом деле не должны пытаться скрыть асинхронность. Общий совет - не писать ни асинхронные оболочки для действительно синхронизирующего кода, ни синхронизирующие оболочки для асинхронного кода. В конечном итоге вы связываете своим потребителям руки за спиной.





Кажется, вы хотите, чтобы ваш метод представился словами: «Я быстр». Правда в том, что время от времени это может быть (очень) медленным. Это потенциально может иметь серьезные последствия.
Заявление
I'm a bottom level function using caches 99.99999% of the time'
неверно, если вы вызываете свой метод один раз в час.
Для потребителей вашего метода лучше видеть: «Я могу работать медленно, но если вы часто звоните мне, я кэширую результат, поэтому быстро вернусь» (это будет GiveJokeOfTheHourAsync() с комментарием).
Если вы хотите, чтобы ваш метод всегда был быстрым, я бы предложил один из следующих вариантов:
UpdateJokeAsync, который вы вызываете, не дожидаясь его в вашем if (HourIsOver). Это будет означать возврат устаревшего результата, пока вы не получите новый.UpdateJokeAsync, чтобы обновить анекдот.
Нет, пожалуйста, прочтите еще раз. Я не работаю асинхронно в 99,99999% случаев. Кроме того, синхронные вызовы и асинхронные вызовы всегда смешиваются, если вы считаете, что любая другая операция, которая не может быть выполнена асинхронно, является синхронной.