6.1 Получение цикла событий
Цикл событий (Event Loop) является центральным компонентом в асинхронном программировании с использованием модуля asyncio в Python. Он управляет выполнением асинхронных задач, обработкой событий и выполнением операций ввода-вывода. Цикл событий позволяет нескольким задачам выполняться одновременно, не блокируя основной поток выполнения.
Создание и получение цикла событий
-
asyncio.get_event_loop(): Возвращает текущий цикл событий или создаёт новый, если текущего нет. -
asyncio.new_event_loop(): Создаёт новый цикл событий. -
asyncio.set_event_loop(loop): Устанавливает указанный цикл событий как текущий.
Пример:
У asyncio есть текущий цикл событий, который содержит все выполняемые задачи. Вы можете получить текущий цикл событий или создать новый и установить его в качестве текущего. Что и происходит в примере ниже.
import asyncio
loop = asyncio.get_event_loop()
print(loop) # Текущий цикл событий
new_loop = asyncio.new_event_loop()
asyncio.set_event_loop(new_loop)
print(asyncio.get_event_loop()) # Новый установленный цикл событий
Стоит отметить, что метод get_event_loop() возвращает текущий активный цикл событий. Создание нового цикла событий и его установка должны использоваться с осторожностью, чтобы избежать конфликтов в асинхронных приложениях.
Запуск цикла событий
-
run_forever(): Запускает цикл событий и продолжает его выполнение до вызоваstop(). -
run_until_complete(future): Запускает цикл событий и завершает его после завершения заданной корутины или будущего объекта.
Пример:
Цикл событий можно запустить в двух режимах: работать бесконечно — что-то типа while True, или пока не выполнится конкретная задача.
import asyncio
async def hello():
print("Hello")
await asyncio.sleep(1)
print("World")
loop = asyncio.get_event_loop()
loop.run_until_complete(hello())
loop.close()
Если вы запустили Event Loop в режиме run_forever(), он будет крутить внутри себя цикл бесконечно. Метод run_forever() окончит работу только если какая-то асинхронная задача вызовет у нашего Event Loop метод stop().
Остановка цикла событий
stop(): Останавливает цикл событий.-
is_running(): ВозвращаетTrue, если цикл событий запущен.
Пример:
Если цикл запущен в бесконечном режиме, он постоянно получает задачи и выполняет их, то сам он не остановится. Кто-то должен получить объект нашего текущего цикла и вызвать у него метод stop(). Чтобы узнать, крутится вечный цикл или нет, нужно вызвать метод is_running().
import asyncio
loop = asyncio.get_event_loop()
loop.stop()
print(loop.is_running()) # False
6.2 Важные методы цикла событий
Метод call_soon(callback, *args)
Планирует вызов функции callback с аргументами *args как можно скорее.
import asyncio
def my_callback():
print("Callback executed")
loop = asyncio.get_event_loop()
loop.call_soon(my_callback)
loop.run_forever()
Помещает функцию callback в самое начало списка задач, чтобы она начала выполняться как можно скорее. В метод можно передавать неасинхронные функции. Этот метод полезен, когда необходимо выполнить задачу с минимальной задержкой, особенно когда требуется незамедлительный отклик в асинхронном приложении.
Метод call_later(delay, callback, *args)
Планирует вызов функции callback с аргументами *args через delay секунд.
import asyncio
def my_callback():
print("Callback executed after delay")
loop = asyncio.get_event_loop()
loop.call_later(2, my_callback)
loop.run_forever()
Этот метод позволяет выполнить отложенный вызов функции: первым параметром передаётся задержка в секундах (может быть дробной), а дальше — ссылка на функцию и её параметры. В метод можно передавать неасинхронные функции. Этот метод можно использовать для управления выполнением задач с разной степенью срочности, что полезно при проектировании сложных асинхронных систем.
Метод call_at(when, callback, *args)
Планирует вызов функции callback с аргументами *args в момент времени when.
import asyncio
import time
def my_callback():
print("Callback executed at specific time")
loop = asyncio.get_event_loop()
when = loop.time() + 2 # Через 2 секунды от текущего времени цикла событий
loop.call_at(when, my_callback)
loop.run_forever()
Если вы хотите запустить задачу не через 5 секунд, а, например, в 15:00 или 24:00, то вам удобнее будет воспользоваться функцией call_at(), которая работает так же, как функция call_soon(), но первым параметром в неё передаётся не длительность паузы, а время, в которое нужно вызвать заданную функцию. В метод можно передавать неасинхронные функции.
Преимущества и особенности
Асинхронное выполнение: Цикл событий позволяет выполнять множество задач параллельно, не блокируя основной поток выполнения.
Эффективное управление ресурсами: Асинхронные операции ввода-вывода выполняются без блокировки, что делает программы более эффективными.
Гибкость и масштабируемость: Цикл событий поддерживает множество методов для планирования задач и обработки событий, что позволяет создавать сложные и масштабируемые асинхронные приложения.
6.3 Взаимодействие с задачами и будущими объектами
Цикл событий управляет выполнением задач (Tasks) и будущих объектов (Futures). Он отслеживает их состояние и обеспечивает их выполнение по мере готовности.
Пример:
import asyncio
async def main():
await asyncio.sleep(1)
print("Task completed")
loop = asyncio.get_event_loop()
task = loop.create_task(main())
loop.run_until_complete(task)
В этом примере показано, как цикл событий управляет выполнением задачи, созданной с помощью метода create_task. Методы call_soon(), call_later() и call_at() можно использовать для управления выполнением задач с разной степенью срочности, что полезно при проектировании сложных асинхронных систем.
ПЕРЕЙДИТЕ В ПОЛНУЮ ВЕРСИЮ