Python 基于产量的协同规划是真正的协同规划吗?
我实现greenlet API只是为了练习Python 基于产量的协同规划是真正的协同规划吗?,python,coroutine,Python,Coroutine,我实现greenlet API只是为了练习 from greenlet import greenlet def test1(): print 12 gr2.switch() print 34 def test2(): print 56 gr1.switch() print 78 gr1 = greenlet(test1) gr2 = greenlet(test2) gr1.switch() 这是我的乱码 def test1(): tm
from greenlet import greenlet
def test1():
print 12
gr2.switch()
print 34
def test2():
print 56
gr1.switch()
print 78
gr1 = greenlet(test1)
gr2 = greenlet(test2)
gr1.switch()
这是我的乱码
def test1():
tmp1=yield
print 12
try:
gv2.send(1)
except StopIteration:
pass
tmp1=yield
print 34
def test2():
tmp2=yield
print 56
try:
gv2.send(1)
except StopIteration:
pass
tmp1=yield
print 78
gv1=test1()
gv1.next()
gv2=test2()
gv2.next()
gv1.send(1)
显示
12
56
Traceback (most recent call last):
File "prog.py", line 26, in <module>
gv1.send(1)
File "prog.py", line 5, in test1
gv2.send(1)
File "prog.py", line 15, in test2
gv2.send(1)
ValueError: generator already executing
12
56
回溯(最近一次呼叫最后一次):
文件“prog.py”,第26行,在
gv1.发送(1)
test1中第5行的文件“prog.py”
gv2.发送(1)
test2中第15行的文件“prog.py”
gv2.发送(1)
ValueError:生成器已在执行
所以我不知道我猜对了
但是看起来在test1将“1”发送到test2之后,它仍然有一些东西
与gevent不同,没有控制流切换。test1仍然具有流
如果不是,我不明白greenlet可以做什么,但python“协同程序”不存在
我的问题是
test2()
的生成器实例正在向自身发送一个值
def test2():
tmp2=yield
print 56
try:
gv2.send(1) # this is the offending line
except StopIteration:
pass
tmp1=yield
print 78
send()
将恢复生成器,但只要在test2()中执行代码,它就已经在运行了。这就是它呕吐的原因
是否要执行:gv1.send(1)
?这也行不通
原因如下:
- 当前情况:在
gv1之前。在示例的最后发送(1)
- gv1处于休眠状态
- gv2处于休眠状态
gv1.send(1)
被调用,这将继续gv1
gv1
进入gv2.发送(1)
- 这将继续
gv2
gv2
进入gv1。发送(1)
gv1
正在恢复,但是,gv1
自上次恢复以来未达到yield
语句。因此,它仍在运行,这就是它也会抛出的原因
本质上,差异可以概括如下:
- greenlet彼此共享一个固有的连接:
.switch()
暂停当前正在执行的greenlet,但会继续
- 另一方面,发电机彼此完全独立。不存在执行生成器的共享上下文。
yield
将“暂停”生成器
next()
/send()
将恢复暂停的生成器,在运行的生成器上调用它们将导致异常
为什么要访问gv2
(它代表了test2
的一个特定实例)?生成器test2()
应该是自包含的,并且不对其使用方式进行任何假设。如果您决定从其他范围调用生成器,该怎么办?不管怎样,向自己发送价值观是没有意义的:你已经拥有了这些价值观。你在寻找什么“提示”?关于到底是什么?哦,这只是个错误,我打算使用“gv1.send(1)”,而我的测试代码实际上就是它。我想知道为什么‘gv1.send(1)’不起作用。关于如何使用基于收益率的‘coroutine’@成功地实现这个例子的“提示”来自未来,这篇文章解释了为什么不起作用;)请参阅“原因如下:”
是的,我读了它,现在明白了异常出现的原因。那么,如果你不介意的话,有没有办法实现第一个呢?如果Python能够做到这一点,那么它将与两个协同程序交互,看起来非常有用it@from__future__您可以创建第三个生成器,在两个生成器之间来回洗牌数据。