likes
comments
collection
share

协程的定义与运行

作者站长头像
站长
· 阅读数 3

1.协程如何定义? 协程的本质还是一个函数,是一个异步函数,在普通的函数上加一个async就行,所以协程的本质是一个异步函数;

2.协程如何运行? 协程直接按照普通函数使用是不会运行的:

async def paly_game(name:str):
    print(name)
paly_game('kpl')

运行结果:

RuntimeWarning: coroutine 'paly_game' was never awaited
  paly_game('kpl')

在现有的库提供了3种方式运行协程: (1)asyncio.run(异步函数/协程)

async def paly_game(name:str):
    print(name)
asyncio.run(paly_game('kpl'))

(2)await 异步函数/协程 利用await调用协程,我们可以看一个例子:

async def paly_game(name:str):
    print(name)
async  def play():
    await paly_game('kpl')#调用paly_game
asyncio.run(play())

需要注意的是,await是必须在函数内部使用,不然会报错:

async def paly_game(name:str):
    print(name)
await paly_game()

运行结果:

await paly_game()
    ^
SyntaxError: 'await' outside function

(3)asyncio.create_task(异步函数/协程),然后运行task

async def paly_game(name:str):
    print(name)
async def play():
    task=asyncio.create_task(paly_game('kpl'))
    await task
asyncio.run(play())

await后面可以跟协程也可以跟协程的task,这两者有什么区别呢? 先看一下直接跟协程:

import asyncio
import time

async def paly_game(name:str,t:int):
    await asyncio.sleep(t)
    print(name)

async def play():
    start=time.time()
    await paly_game('kpl',2)
    await paly_game('kpl',3)
    print('spend total time is {}'.format(time.time()-start))
asyncio.run(play())

运行结果:

kpl
kpl
spend total time is 5.016455888748169

我们发现好像协程根本没有生效,还是3+2=5秒,实际上,只有使用task才会有类似于调度的协程发生:

import asyncio
import time

async def paly_game(name:str,t:int):
    await asyncio.sleep(t)
    print(name)
async def play():
    start=time.time()
    task1=asyncio.create_task(paly_game('kpl',2))
    task2 = asyncio.create_task(paly_game('kpl', 3))
    await task1
    await task2
    print('spend total time is {}'.format(time.time()-start))
asyncio.run(play())

运行结果:

kpl
kpl
spend total time is 2.995018243789673

现在我们的协程才会生效。