插件窝 干货文章 Python事件驱动编程:如何用asyncio实现高效的异步操作?

Python事件驱动编程:如何用asyncio实现高效的异步操作?

asyncio 任务 个协 获取 269    来源:    2025-03-14

在Python中,asyncio 是一个用于编写单线程并发代码的库,使用 async/await 语法。它非常适合用于I/O密集型和高层级结构化网络代码。以下是如何使用 asyncio 实现高效的异步操作的基本步骤和示例。

1. 基本概念

  • 协程 (Coroutine): 使用 async def 定义的函数,它可以在执行过程中暂停和恢复。
  • 事件循环 (Event Loop): 管理和调度协程的执行。
  • 任务 (Task): 一个协程的封装,用于调度执行。

2. 基本步骤

  1. 定义协程: 使用 async def 定义协程函数。
  2. 创建事件循环: 使用 asyncio.get_event_loop() 获取事件循环。
  3. 运行协程: 使用 loop.run_until_complete() 运行协程。

3. 示例代码

import asyncio

# 定义一个简单的协程
async def say_after(delay, message):
    await asyncio.sleep(delay)
    print(message)

# 主协程
async def main():
    print("开始执行")

    # 创建任务
    task1 = asyncio.create_task(say_after(1, 'Hello'))
    task2 = asyncio.create_task(say_after(2, 'World'))

    # 等待任务完成
    await task1
    await task2

    print("执行结束")

# 获取事件循环并运行主协程
loop = asyncio.get_event_loop()
loop.run_until_complete(main())
loop.close()

4. 解释

  • say_after 协程: 这个协程会在指定的延迟后打印消息。
  • main 协程: 这是主协程,它创建了两个任务 task1task2,并等待它们完成。
  • asyncio.create_task: 将协程封装为任务,以便并发执行。
  • await: 用于等待协程或任务完成。

5. 高级用法

  • 并发执行多个协程: 使用 asyncio.gather 可以并发执行多个协程。
  • 超时控制: 使用 asyncio.wait_for 可以设置超时。
  • 任务取消: 使用 task.cancel() 可以取消任务。

6. 并发执行示例

import asyncio

async def fetch_data(delay, id):
    print(f"开始获取数据 {id}")
    await asyncio.sleep(delay)
    print(f"数据 {id} 获取完成")
    return f"数据 {id}"

async def main():
    # 并发执行多个协程
    results = await asyncio.gather(
        fetch_data(2, 1),
        fetch_data(1, 2),
        fetch_data(3, 3),
    )
    print("所有数据获取完成:", results)

# 运行主协程
asyncio.run(main())

7. 超时控制示例

import asyncio

async def fetch_data(delay, id):
    print(f"开始获取数据 {id}")
    await asyncio.sleep(delay)
    print(f"数据 {id} 获取完成")
    return f"数据 {id}"

async def main():
    try:
        # 设置超时
        result = await asyncio.wait_for(fetch_data(5, 1), timeout=2.0)
        print("获取数据成功:", result)
    except asyncio.TimeoutError:
        print("获取数据超时")

# 运行主协程
asyncio.run(main())

8. 任务取消示例

import asyncio

async def fetch_data(delay, id):
    print(f"开始获取数据 {id}")
    await asyncio.sleep(delay)
    print(f"数据 {id} 获取完成")
    return f"数据 {id}"

async def main():
    task = asyncio.create_task(fetch_data(5, 1))
    await asyncio.sleep(2)  # 等待2秒
    task.cancel()  # 取消任务
    try:
        await task
    except asyncio.CancelledError:
        print("任务被取消")

# 运行主协程
asyncio.run(main())

9. 总结

通过 asyncio,你可以轻松地编写高效的异步代码,特别是在处理I/O密集型任务时。掌握 asyncio 的基本用法和高级特性,可以显著提升程序的性能和响应速度。