我在玩 pykka 的演员模型,发现了一些有趣的行为。这是一个演示
- 启动一个演员
- 获取它的代理
- 设置其@properties 之一
这是代码:
import time
import pykka
from sys import version_info as python_version
if python_version > (3, 0):
from _thread import get_ident
else:
from thread import get_ident
startTime = time.time()
def debug(msg, prefix='MSG'):
msgProc = "%s (thread #%s @ t = %.2fs): %s" % (prefix,get_ident(), time.time() - startTime, msg)
print(msgProc)
def mainThread():
debug('Launching support actor...', prefix='MAIN')
supportRef = supportThread.start()
debug('Getting support proxy...', prefix='MAIN')
supportProxy = supportRef.proxy()
debug('Getting myVal obj...', prefix='MAIN')
obj = supportProxy.myVal
debug(obj, prefix='MAIN')
debug('Setting myVal obj...', prefix='MAIN')
supportProxy.myVal = 2
debug('Setting myVal obj...', prefix='MAIN')
supportProxy.myVal = 3
supportProxy.stop()
class supportThread(pykka.ThreadingActor):
def __init__(self):
super(supportThread, self).__init__()
self._myVal = 0
@property
def myVal(self):
debug("Getting value", prefix='SUPPORT')
return self._myVal
@myVal.setter
def myVal(self, value):
debug("Setting value: processing for 1s...", prefix='SUPPORT')
time.sleep(1)
debug("Setting value: done", prefix='SUPPORT')
self._myVal = value
mainThread()
输出如下所示:
MAIN (thread #16344 @ t = 0.00s): Launching support actor...
MAIN (thread #16344 @ t = 0.00s): Getting support proxy...
SUPPORT (thread #16344 @ t = 0.00s): Getting value
MAIN (thread #16344 @ t = 0.00s): Getting myVal obj...
MAIN (thread #16344 @ t = 0.00s): <pykka.threading.ThreadingFuture object at 0x0000000002998518>
MAIN (thread #16344 @ t = 0.00s): Setting myVal obj...
SUPPORT (thread #16248 @ t = 0.00s): Getting value
SUPPORT (thread #16248 @ t = 0.00s): Setting value: processing for 1s...
SUPPORT (thread #16248 @ t = 1.00s): Setting value: done
MAIN (thread #16344 @ t = 1.00s): Setting myVal obj...
SUPPORT (thread #16248 @ t = 1.01s): Setting value: processing for 1s...
SUPPORT (thread #16248 @ t = 2.01s): Setting value: done
[Finished in 2.3s]
我在这里有几个问题。
- 为什么 getter
supportThread.myVal()
在被调用时会在主线程的上下文中.proxy()
被调用? - 为什么这些行会
supportProxy.myVal = <a new value>
导致主线程等待actor完成?
这对我来说似乎是一个错误:我认为只有.get()
在 ThreadingFuture 上调用代理时才应该阻止执行。或者这是故意的?