async python - 从引发AssertionError获取正确的参数

问题描述 投票:0回答:1

我的要求是同时运行2个函数,如果另一个函数计算并更快地返回结果,则停止执行一个函数。

我知道异步编程或事件循环的知识。我读了引导我到python 3.6asyncio.wait()

我的示例代码:

import time
import asyncio as aio

async def f(x):
    time.sleep(1) # to fake fast work
    print("f say: " + str(x*2))
    return x*2

async def s(x):
    time.sleep(3) # to fake slow work
    print("s say: " + str(x*2))
    return x**2

x = 10

assert aio.iscoroutinefunction(f)
assert aio.iscoroutinefunction(s)

futures = {f(x), s(x)}

def executor():
    yield from aio.wait(futures, return_when=aio.FIRST_COMPLETED)

done, pending = executor()

但它不是出于某种未知原因而起作用。

python asynchronous python-asyncio
1个回答
1
投票

你得到的特殊断言与错误使用yield from有关。然而,问题更深入:

我的要求是同时运行2个函数

这不是asyncio如何工作,没有“同时”运行。相反,一个人运行异步函数,这些函数执行到他们达到通常阻塞调用的时间点。而不是阻塞,异步函数然后暂停其执行,允许其他协同程序运行。它们必须由事件循环驱动,该事件循环驱动它们并在某些IO事件允许它们恢复时唤醒它们。

更正确的asyncio版本的代码如下所示:

import asyncio

async def f(x):
    await asyncio.sleep(1) # to fake fast work
    print("f say: " + str(x*2))
    return x*2

async def s(x):
    await asyncio.sleep(3) # to fake slow work
    print("s say: " + str(x*2))
    return x**2

async def execute():
    futures = {f(10), s(10)}
    done, pending = await asyncio.wait(futures, return_when=asyncio.FIRST_COMPLETED)
    for fut in pending:
        fut.cancel()
    return done

loop = asyncio.get_event_loop()
done = loop.run_until_complete(execute())
print(done)

特别注意:

  • 使用asyncio.sleep()而不是time.sleep()。这适用于每个阻止呼叫。
  • 必须使用asyncio.sleep关键字等待asyncio.waitawait等协同程序。这允许协程在遇到阻塞呼叫时暂停。
  • 异步代码通过事件循环执行,其入口点通常为run_until_completerun_forever
© www.soinside.com 2019 - 2024. All rights reserved.