背景:我是一个经验丰富的Python程序员,对新的coroutines/async/await特性一无所知。我不能写一个异步的“hello world”来救我的命。在
我的问题是:我得到了一个任意的协同程序函数f
。我想写一个协同程序函数g
,它将包装f
,也就是说,我将把g
交给用户,就像它是{g
将在幕后使用{
我想添加的功能:每当程序流进入我的协同程序时,它就会获得我提供的上下文管理器,一旦程序流离开协同程序,它就会释放上下文管理器。流回来了?重新获取上下文管理器。它又出来了?重新释放它。直到合作计划完成。在
为了演示,下面介绍了普通生成器的功能:
def generator_wrapper(_, *args, **kwargs):
gen = function(*args, **kwargs)
method, incoming = gen.send, None
while True:
with self:
outgoing = method(incoming)
try:
method, incoming = gen.send, (yield outgoing)
except Exception as e:
method, incoming = gen.throw, e
可以用协同程序来完成吗?
协程建立在迭代器上,^{} special method 是一个常规迭代器。这允许您将底层迭代器包装在另一个迭代器中。诀窍在于,必须使用目标的迭代器
__await__
展开,然后使用自己的__await__
重新包装自己的迭代器。在用于实例化协同程序的核心功能如下所示:
注意,这在}。在
Coroutine
上显式工作,而不是Awaitable
-Coroutine.__await__
实现生成器接口。理论上,Awaitable
不一定提供__await__().send
或{这足以将消息传入和传出:
^{pr2}$您可以将包装部分委托给一个单独的装饰器。这还可以确保您有一个实际的协同程序,而不是一个自定义类-一些异步库需要这样做。在
这允许您直接装饰协同程序函数:
相关问题 更多 >
编程相关推荐