Асинхронне програмування в C# 5

03.10.2016

Асинхронне програмування в C# 5

Асинхронне програмування в C# 5

Висновок

Асинхронне програмування в C# 5

Всі знають, що синхронне виконання тривалих операцій – це погано. Це погано з багатьох причин, починаючи з того, що синхронні виклики призводять до подвисанию користувальницького інтерфейсу, поганий масштабованості і розширюваності, закінчуючи тим, що ви не зможете скористатися усіма можливостями багатоядерного процесора вашого домашнього комп’ютера, не кажучи вже про переваги асинхронного вводу/виводу, ефективність якого виявляється навіть на одноядерних процесорах. Про тему асинхронності та багатопоточності говорять на кожному кроці, починаючи від відомих авторів, на зразок Джеффрі Ріхтера, Джо Даффі або Джозефа Албахарі, і закінчуючи безліччю статей на кожному другому технічному сайті і обов’язковим питанням на співбесіді типу «А скільки ви знаєте способів виконати операцію асинхронно?».

Однією з причин такого стану справ є те, що вся підтримка багатопоточності в мові C# закінчується оператором lock, а все інше прикручені до нього за допомогою бібліотек, починаючи з BCL і RX, закінчуючи Power Threading та іншими «велосипедами» різного виду і форми (хоча потрібно визнати, що головна причина полягає в тому, що теми багатопоточності і асинхронності самі по собі досить складні, і всі спроби спростити їх настільки, щоб вони були зрозуміла домогосподаркам, успіхом не увінчались і навряд чи увінчаються коли-небудь). Проте, як говорилося в недавньому доповіді Андерса Хейлсберга на конференції Microsoft PDC, щастя має настати з виходом нової версії мови C#, у якому робота з синхронними операціями буде додана на рівні мови. Однак перш ніж приступати до розгляду можливостей, які в черговий раз мають спростити рішення асинхронних завдань, слід ближче розглянути проблеми, які виникають при використанні синхронних операцій і те, як ці проблеми вирішувалися досі.

Синхронне і асинхронне виконання операцій

Для початку треба відповісти на дуже просте питання: навіщо нам взагалі потрібна вся ця асинхронність, і чому нам не вистачає старих добрих синхронних операцій, ну або максимум асинхронного виконання операції за допомогою того ж пулу потоків.

Дуже популярним прикладом виконання асинхронних операцій є звернення до якого-небудь зовнішнього ресурсу типу Web-сервісу, доступ до Web-сторінки або асинхронний доступ до файлу. І хоча в якості прикладу з тим же успіхом можна використовувати метод з тілом виду Sleep(5000), зробимо вигляд, що ми намагаємося вирішити дану задачу, наприклад, написати свій власний Web-браузер з підтримкою декількох вкладок.

Отже, давайте розглянемо синхронну версію функції, що звертається до заданих Web-сторінок і виводить на екран довжини отриманих відповідей (не занадто функціонально для цього Web-браузера, але треба ж з чогось починати):

Всі ці операції можна виконати в циклі, але це буде не настільки показова з точки зору можливостей розпаралелювання цих операцій; крім того, часто буває потрібно виконати кілька різних асинхронних операцій, які об’єднати в цикл ніяк не вийде.

Оскільки ідея асинхронного виконання далеко не нова, класи, подібні WebRequest (і його спадкоємцю HttpWebRequest) підтримують спеціальний набір функцій, які дозволяють виконувати тривалі операції асинхронно за допомогою методів BeginGetResponse і EndGetResponse. Традиційно така модель називається APM – Asynchronous Programming Model.

Тепер основний потік виконує тільки запити на виконання асинхронних операцій, а самі операції виконуються в робочих потоках пулу потоків і велику частину часу спить, чекаючи на завершення операцій вводу/виводу. Це дозволяє запустити практично одночасно всі три запиту вводу/виводу і незалежно очікувати завершення кожного з них. Цей код виглядає досить просто, проте спроба зберегти результати всіх трьох асинхронних операцій у файл (причому теж асинхронно) з повноцінною обробкою помилок, зробить код значно більш складним для розуміння і супроводу. Крім того, додавання функцій зворотного виклику для обробки результатів асинхронних операцій змінює потік управління таким чином, що стають недоступні такі зручні допоміжні мовні конструкції, як блоки try/catch/finally, lock або using.

Асинхронне програмування в C# 5

Короткий опис статті: програмування на c У статті розглядаються нові можливості асинхронного програмування доступні в новій версії мови програмування C#. C# 5; асинхронне програмування; багатопоточність

Джерело: Асинхронне програмування в C# 5

Також ви можете прочитати