● 相对于前两个函数,gather的使用频率更高,因为它支持多个协程任务“同时”执行
● 理解__await__ __iter__的使用
● 理解关键字async/await,async/await是3.5之后的语法,和yield/yield from异曲同工
● 今天的文章有点长,请大家耐心看完
二、环境准备 组件 版本
python 3.7.7
三、run的实现
先来看下官方gather的使用方法:
|># more main.py import asyncio async def hello(): print('enter hello ...') return 'return hello ...' async def world(): print('enter world ...') return 'return world ...' async def helloworld(): print('enter helloworld') ret = await asyncio.gather(hello(), world()) print('exit helloworld') return ret if __name__ == "__main__": ret = asyncio.run(helloworld()) print(ret) |># python3 main.py enter helloworld enter hello ... enter world ... exit helloworld ['return hello ...', 'return world ...']来看下造的轮子的使用方式:
▶ more main.py import wilsonasyncio async def hello(): print('enter hello ...') return 'return hello ...' async def world(): print('enter world ...') return 'return world ...' async def helloworld(): print('enter helloworld') ret = await wilsonasyncio.gather(hello(), world()) print('exit helloworld') return ret if __name__ == "__main__": ret = wilsonasyncio.run(helloworld()) print(ret) ▶ python3 main.py enter helloworld enter hello ... enter world ... exit helloworld ['return hello ...', 'return world ...']自己造的轮子也很好的运行了,下面我们来看下轮子的代码
四、代码解析轮子代码
1)代码组成
|># tree . ├── eventloops.py ├── futures.py ├── main.py ├── tasks.py ├── wilsonasyncio.py 文件 作用eventloops.py 事件循环
futures.py futures对象
tasks.py tasks对象
wilsonasyncio.py 可调用方法集合
main.py 入口
2)代码概览:
eventloops.py
类/函数 方法 对象 作用 描述Eventloop 事件循环,一个线程只有运行一个
__init__ 初始化两个重要对象 self._ready 与 self._stopping
self._ready 所有的待执行任务都是从这个队列取出来,非常重要
self._stopping 事件循环完成的标志
call_soon 调用该方法会立即将任务添加到待执行队列
run_once 被run_forever调用,从self._ready队列里面取出任务执行
run_forever 死循环,若self._stopping则退出循环
run_until_complete 非常重要的函数,任务的起点和终点(后面详细介绍)
create_task 将传入的函数封装成task对象,这个操作会将task.__step添加到__ready队列
Handle 所有的任务进入待执行队列(Eventloop.call_soon)之前都会封装成Handle对象
__init__ 初始化两个重要对象 self._callback 与 self._args
self._callback 待执行函数主体
self._args 待执行函数参数
_run 待执行函数执行
get_event_loop 获取当前线程的事件循环
_complete_eventloop 将事件循环的_stopping标志置位True
run 入口函数
gather 可以同时执行多个任务的入口函数 新增
_GatheringFuture 将每一个任务组成列表,封装成一个新的类 新增