Как я мог достичь sh Node.js, как асинхронность с C#? - PullRequest
0 голосов
/ 27 марта 2020

Я работаю с Node.js, и поэтому я очень привык к его «стилю программирования» и его способу работать с асинхронными операциями с помощью функций более высокого порядка и обратных вызовов, где большинство событий ввода-вывода обрабатываются в асинхронном режиме c если я хочу выполнить операцию syn c, мне нужно использовать Promises или ярлык await, тогда как в синхронных языках программирования, таких как Java, C#, C ++, очевидно, мне придется делать наоборот, как-то сообщая компилятору, что задача, которую я хочу достичь, должна выполняться асинхронно. Я пытался читать документы Microsoft и не мог понять, как этого добиться. Я имею в виду, что я мог бы использовать Threads, но для простой задачи, которую я хочу обработать, исследование Threads просто не стоит того, чтобы гарантировать безопасность потоков. Я наткнулся на класс Task. Итак, предположим, что я хочу запускать метод Task несколько раз асинхронно c, где функции вызываются параллельно. Как я могу это сделать?

        private Task<int> MyCustomTask(string whatever)
        {
           // I/O event that I want to be processed in async manner
        }

Итак, я хотел запустить этот метод параллельно, без многопоточности.

foreach (x in y)
{
   MyCustomTask("");
}

Ответы [ 2 ]

2 голосов
/ 27 марта 2020

Если вы не хотите ждать, вы можете сделать что-то вроде этого.

public class AsyncExamples
{
    public List<string> whatevers = new List<string> { "1", "2", "3" };

    private void MyCustomTask(string whatever)
    {
        // I/O event that I want to be processed in async manner
    }

    public void FireAndForgetAsync(string whatever)
    {
        Task.Run(
            () =>
            {
                MyCustomTask(whatever);
            }
        );
    }

    public void DoParallelAsyncStuff()
    {
        foreach (var whatever in whatevers)
        {
            FireAndForgetAsync(whatever);
        }
    }
}
1 голос
/ 27 марта 2020

большинство событий ввода / вывода обрабатываются асинхронно c способом, и если я хочу выполнить операцию syn c, мне нужно использовать Promises или ярлык await

Я полагаю, что разница, которую вы выражаете, заключается в разнице между функциональным и императивным программированием, а не в разнице между асинхронным и синхронным программированием. Поэтому я думаю, что вы говорите, что асинхронное программирование более естественно соответствует функциональному стилю, с чем я бы согласился. JavaScript в основном функциональный, хотя он также имеет императивные и OOP аспекты. C# является более обязательным и OOP, чем функциональным, хотя с каждым годом он становится все более функциональным.

Однако и JavaScript, и C# являются синхронными по умолчанию, а не асинхронными по умолчанию. Метод должен «включить» асинхронность, используя async / await. Таким образом, они очень похожи.

Я пытался читать документы Microsoft и не мог понять, как этого достичь.

Шпаргалка, если вы ' Вы знакомы с асинхронным JavaScript:

  • Task<T> is Promise<T>
    • Если вам нужно написать оболочку для другого API (например, конструктор Promise<T> с использованием resolve / reject), тогда вам необходим C# тип TaskCompletionSource<T>.
  • async и await работают практически одинаково.
  • Task.WhenAll равно Promise.all, а Task.WhenAny равно Promise.any. Не существует встроенного эквивалента для Promise.race.
  • Task.FromResult равно Promise.resolve, а Task.FromException равно Promise.reject.

Так Предположим, что я хочу запустить метод Task несколько раз в асинхронном режиме c, где функции вызываются параллельно. Как я могу это сделать?

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

Чтобы сделать это в JS, вы взял бы итерацию, map по методу async (результатом чего будет итерация обещаний), а затем Promise.all эти обещания.

Чтобы сделать то же самое в C#, вы бы возьмите свой перечислимый, Select его по методу async (в результате чего получается множество задач), а затем Task.WhenAll этих задач.

var tasks = y.Select(x => MyCustomTask(x)).ToList();
await Task.WhenAll(tasks);
...