我正在学习多处理模块和装饰器。关于下面的代码,我有两个问题:
from time import sleep
from multiprocessing import Process
class async:
def __init__(self, function):
self.func = function
def __call__(self, *args, **kwargs):
p = Process(target = self.func, args = args, kwargs = kwargs)
p.start()
@async
def printA():
sleep(1)
print("A")
def main():
printA()
printA()
printA()
#do more work
if __name__ == "__main__":
main()
现在我得到了PicklingError: Can't pickle <function printA at 0x00000273F97FF1E0>: it's not the same object as __main__.printA
我不知道怎么解决这个问题。我觉得这是在我工作的unix机器上运行的,是Windows的东西吗?
我希望子进程在完成时自动终止。我尝试在结尾用sys.exit()
包装函数,并将其作为进程的目标,但是sys.exit()
似乎无法正确终止僵尸进程。正确的方法是什么?
我不想阻塞join()
,也不想设置daemon=True
。最终目标是有人可以导入这个模块,将@async放在任何函数上,它将在一个单独的进程中运行,然后在到达函数末尾时自行终止。在
酸洗错误:我可以重现该问题。在Linux上它工作得很好,在Windows上就不行了。问题似乎出在Windows上不能正确地处理装饰器。删除decorator会导致这段工作代码(当然这不是您想要的,但可能会说服您尝试另一种设计方法)。还有一个this thread on SO也有完全相同的问题。在
僵尸进程:为了避免僵尸进程,您需要让父进程读取其子进程的退出代码,您需要在父进程中对子进程运行
join()
来完成此操作。你可以像这样在装饰店里这样做:这使用了python只执行
@async
的一个实例的效果,因此您可以收集self.pool
中的所有进程。注意,这只在主进程的出口运行,因为python不会在前面删除异步实例。在相关问题 更多 >
编程相关推荐