可等待对象
如果一个对象可以在 await 语句中使用,那么它就是 可等待 对象。许多 asyncio API 都被设计为接受可等待对象。
可等待 对象有三种主要类型: 协程, 任务 和 Future.
协程
协程 属于 可等待 对象,通过 async/await 语法进行声明,是编写 asyncio 应用的推荐方式。
协程函数: 定义形式为 async def 的函数;协程对象: 调用 协程函数 所返回的对象。
注意:简单地调用一个协程函数并不会立即执行,只是返回一个协程对象。
使用 asyncio.run() 函数来调用协程对象,协程函数才会被真正执行。
示例1:
>>> import asyncio
>>> async def main():
...     print('hello')
...     await asyncio.sleep(1)
...     print('world')
>>> main()
<coroutine object main at 0x1053bb7c8>
>>> asyncio.run(main())
hello
world
示例2:
import asyncio
async def nested():
    return 42
async def main():
    # 此处仅仅创建了一个协程对象,nested函数并没有真正执行。
    # 必须使用 await 关键字,后面可用asyncio.run()函数调用执行。
    nested()
    # 使用 await 关键字
    print(await nested())  # will print "42".
main())
任务
任务 被用来设置日程以便 并发 执行协程。【个人理解:协程无法直接并发执行,必须打包成任务】
创建任务
asyncio.create_task(coro, *, name=None)
将 协程对象 coro 打包为一个 Task 任务,排入日程准备执行。 返回 Task 对象。
name 不为 None,它将使用 Task.set_name() 来设为任务的名称。
该任务会在 get_running_loop() 返回的循环中执行,如果当前线程没有在运行的循环则会引发 RuntimeError。
休眠
coroutine asyncio.sleep(delay, result=None, *, loop=None)
并发运行任务
awaitable asyncio.gather(*aws, loop=None, return_exceptions=False)
并发 运行 aws 序列中的 可等待对象.
如果 aws 中的某个可等待对象为协程,它将自动作为一个任务(自动创建Task对象)加入日程。
如果所有可等待对象都成功完成,结果将返回一个由所有返回值聚合而成的列表。
示例代码:
import asyncio
import time
# 并发执行协程
# 模拟的耗时任务 交给协程来处理
async def my_task(name, number):
    await asyncio.sleep(number)
    print('%s 已经完成任务...' % name)
    return number
async def main():
    print(f"started at {time.strftime('%X')}")
    # 将三个任务交给 asyncio.gather 并发执行。预期耗时4秒,否则未达到预期
    main_res = await asyncio.gather(
        my_task('A', 2),
        my_task('B', 3),
        my_task('C', 4),
    )
    
    # 压缩参数为列表变量的形式
    # task_list = [my_task('A', 2), my_task('B', 2), my_task('C', 4)]
    # main_res = await asyncio.gather(*task_list)
    # 以下方法为并发异步执行,可达相同预期。 但在协程较多时,推荐使用上法
    # task1 = asyncio.create_task(my_task('A', 2))
    # task2 = asyncio.create_task(my_task('B', 3))
    # task3 = asyncio.create_task(my_task('C', 4))
    # await task1
    # await task2
    # await task3
    # 返回一个由所有返回值聚合而成的列表
    print(main_res)
    print(f"finished at {time.strftime('%X')}")
asyncio.run(main())
结果如下:
started at 14:46:26
A 已经完成任务...
B 已经完成任务...
C 已经完成任务...
[2, 3, 4]
finished at 14:46:30
- async def my_task(name, number)为需要并发执行的- 异步方法.
- 通过 await asyncio.gather(),对多个并发执行的函数方法,进行调用。
- 将 await asyncio.gather()放入async def main()方法函数中使用。
- 使用 asyncio.run(main())调用async def main()方法
asyncio 异步 I/O https://docs.python.org/zh-cn/3.9/library/asyncio.html
简单粗暴有效上手Python3异步asyncio https://blog.csdn.net/lpwmm/article/details/102985040
Python3.7 高级编程之 async/await asyncio 通过任务gather并发运行协程 https://blog.csdn.net/haeasringnar/article/details/100181731
 沙滩星空的博客
沙滩星空的博客