Python中asyncio.as_completed()标注接受Iterable,传入Generator却崩溃?
问题原因解析
1. asyncio.as_completed 运行时的迭代特性要求
Python 3.7 版本的 asyncio.as_completed() 内部实现会对传入的可迭代对象进行多次遍历:第一次遍历是为了将所有任务提交到事件循环调度,第二次遍历是为了等待任务完成并返回结果。
但生成器属于一次性可迭代对象,第一次遍历后就会被耗尽,第二次遍历时就没有元素了,这就触发了 TypeError——因为函数预期能获取到有效的任务/futures,而不是空的生成器。
而列表是可重复迭代的序列类型,多次遍历都能拿到完整的任务集合,所以转成 list 后可以正常运行。
2. 类型提示与运行时实现的差异
虽然 asyncio.as_completed() 的类型提示标注为接受 Iterable 类型,但这只是静态层面的约束,实际运行时它要求的是支持多次迭代的 Iterable。生成器虽然属于 Iterable 范畴,但不满足多次迭代的要求,因此出现了类型提示和运行时行为不一致的情况。
额外提示:代码中的小疏漏
你的 sleep() 函数里漏写了 await,正确写法应该是:
async def sleep(): await asyncio.sleep(1)
这个疏漏不影响当前的 TypeError,但会导致任务不会真正休眠,建议补上。
内容的提问来源于stack exchange,提问作者Ivan GJ
相关产品推荐
相关产品推荐

