python学习05协程_async使用

async/await使用
async/await:用于定义协程的关键字,async定义一个协程,await用于挂起阻塞的异步调用接口
event_loop:事件循环,程序开启一个无限的循环,程序员把一些函数注册到事件循环上。当满足事件发生时,调用相应的协程函数
coroutine:协程对象,指一个使用async关键字定义的函数,它的调用不会立即执行函数,而是返回一个协程对象。
协程对象需要注册到事件循环,由事件循环调用。
task:任务,是对协程进一步封装,其中包含任务的各种状态。
future:代表将来执行或没有执行的任务结果。它和task没有本质区别
#1、创建协程,在def前加上async的声明,就完成了一个协程函数的定义

协程对象不能直接调用运行,需要将协程注册到事件循环,并启动事件循环才能使用

import asyncio

#定义协程函数
async def func(a):
    print(a)

#调用协程函数,生成一个协程对象,此时协程函数并未执行
coroutine = func('hello world')
#创建事件循环
loop = asyncio.get_event_loop()
#将协程添加到事件循环,并启动
loop.run_until_complete(coroutine)

#任务对象task
'''
协程对象不能直接运行,在注册事件循环的时候,其实run_until_complete方法将协程包装成为一个任务task对象
也可以将协程包装程任务
'''
#实现方式1:使用create_task
async def func1(a):
    print(a)
    return a
coroutine = func1('hello world')
loop = asyncio.get_event_loop()
#使用create_task()创建task,并将coroutine对象转化成task对象
task = loop.create_task(coroutine)
print(f'task:{task}')
loop.run_until_complete(task)
print(f'task:{task}')

#实现方式2:使用asyncio的ensure_future()方法,创建task
coroutine = func('hello world')
task = asyncio.ensure_future(coroutine)
loop = asyncio.get_event_loop()
print(f'task:{task}')
loop.run_until_complete(task)
print(f'task:{task}')

#实现方式3:绑定回调函数
'''
如果需要在task执行完毕后对结果进行处理,可以通过task绑定回调函数完成,回调的最后一个参数是future对象
'''
def callback(task):
    print(f'result:{task.result()}')

coroutine = func('hello world')
loop = asyncio.get_event_loop()
task = loop.create_task(coroutine)
task.add_done_callback(callback)
print(f'task:{task}')
loop.run_until_complete(task)
print(f'task:{task}')

'''
如果需要执行多个任务时,可以定义一个任务列表,将需要完成的协程任务都加进去。将原本的loop.run_until_complete(tasks)
改为loop.run_complete(asyncio.wait(tasks))
如果执行的是多个耗时的任务,如网络请求、文件读取等,可以使用await。await可以针对耗时的操作进行挂起,就像生成器里的yield一样,函数让出控制权
协程遇到await,事件循环将会挂起该协程,执行别的协程,直到其他的协程也挂起或执行完毕,再进行下一个协程的执行。
'''
import time

async def task1():
    print('开始运行io任务1。。。')
    await asyncio.sleep(2)
    print('io 任务1已完成,耗时2s')
    return task1.__name__

async def task2():
    print('开始运行io任务2。。。')
    await asyncio.sleep(3)
    print('io任务2已完成,耗时3s')
    return task2.__name__
#
if __name__ == '__main__':
     start = time.time()
     loop = asyncio.get_event_loop()
     tasks = [task1(),task2()]
     loop.run_until_complete(asyncio.wait(tasks))
     print('所有io任务总耗时%.5f秒'%float(time.time()-start))

#使用asyncio.run()方法

async def main():
    print('hello ...')
    await asyncio.sleep(1)
    print('...world')

asyncio.run(main())

你可能感兴趣的:(python学习,python,学习,开发语言)