Python 协程与异步编程实战
本文由一缘原创整理,系统梳理 Python 协程与异步编程的原理、asyncio、实战技巧,适合所有 Python/后端开发者。
Python 协程与异步编程实战
协程是 Python 高性能并发的核心,asyncio 是官方异步编程标准库。
1. 什么是协程?
- 协程是一种用户态的轻量级线程(微线程)
- 通过
async def
定义,await
挂起等待
2. async/await 基本用法
import asyncio
async def hello():
print('Hello ...')
await asyncio.sleep(1)
print('... World!')
asyncio.run(hello())
输出:
Hello ...
(1秒后)
... World!
3. asyncio 事件循环
- 事件循环负责调度所有协程任务
asyncio.run()
自动创建和关闭事件循环
4. Task 与 Future
- Task 是对协程的进一步封装,支持并发调度
- Future 表示一个尚未完成的结果
import asyncio
async def foo():
await asyncio.sleep(1)
return 42
async def main():
task = asyncio.create_task(foo())
print('Task created')
result = await task
print('Result:', result)
asyncio.run(main())
输出:
Task created
(1秒后)
Result: 42
5. 并发 vs 并行
- 并发:单线程下切换任务(协程)
- 并行:多线程/多进程同时执行
import asyncio
async def work(n):
print(f'start {n}')
await asyncio.sleep(1)
print(f'end {n}')
async def main():
await asyncio.gather(work(1), work(2), work(3))
asyncio.run(main())
输出:
start 1
start 2
start 3
(1秒后)
end 1
end 2
end 3
6. 协程中的异常处理
import asyncio
async def error():
raise ValueError('出错了')
async def main():
try:
await error()
except Exception as e:
print('捕获异常:', e)
asyncio.run(main())
输出:
捕获异常: 出错了
7. 实战:异步爬虫
import asyncio
import aiohttp
async def fetch(url):
async with aiohttp.ClientSession() as session:
async with session.get(url) as resp:
return await resp.text()
async def main():
urls = ['https://httpbin.org/delay/1'] * 3
results = await asyncio.gather(*(fetch(url) for url in urls))
print([len(r) for r in results])
asyncio.run(main())
输出:
[...3个页面内容长度...]
8. 协程的最佳实践
- 优先用 asyncio 官方库,避免滥用线程/进程
- 用 gather 并发调度,合理处理异常
- 避免阻塞操作(如 time.sleep、同步 I/O)
- 善用 async with、async for
结语
协程和异步编程是 Python 高性能后端的核心,理解 asyncio 能让你写出高并发、可扩展的应用。欢迎留言交流更多 Python 深度问题!