max*_*max 8 python multiprocessing python-3.x python-multiprocessing
docs(python 3.4)解释说spawn,"子进程只会继承运行进程对象run()方法所需的那些资源".
但哪些对象是"必要的"?我读它的方式告诉我,从内部可以到达的所有对象run()都是"必要的",包括传递args给的参数Process.__init__,加上存储在全局变量中的任何东西,以及在全局范围内定义的类,函数及其属性.但是,这是不正确的; 以下代码确认不会继承存储在全局变量中的对象:
# running under python 3.4 / Windows
# but behaves the same under Unix
import multiprocessing as mp
x = 0
class A:
y = 0
def f():
print(x) # 0
print(A.y) # 0
def g(x, A):
print(x) # 1
print(A.y) # 0; really, not even args are inherited?
def main():
global x
x = 1
A.y = 1
p = mp.Process(target = f)
p.start()
q = mp.Process(target = g, args = (x, A))
q.start()
if __name__=="__main__":
mp.set_start_method('spawn')
main()
Run Code Online (Sandbox Code Playgroud)
是否有明确的规则说明哪些对象是继承的?
编辑:
要确认:在Ubuntu上运行它会产生相同的输出.(感谢@mata澄清,我忘添加global x到main()这种省略使我示例混淆;它也将影响结果,如果我是切换'spawn'到'fork'在Ubuntu下我现在加入global x到上面的代码).
这与发送到生成的进程时类被pickle的方式有关.类的pickle版本并不真正包含其内部状态,而只包含模块和类的名称:
class A:
y = 0
pickle.dumps(A)
# b'\x80\x03c__main__\nA\nq\x00.'
Run Code Online (Sandbox Code Playgroud)
这里没有关于y它的信息,它与类的引用相当.
当作为argumeht传递时,该类将在生成的进程中进行unpickled,如果需要g,将导入其模块(此处__main__)并返回对类的引用,因此在main函数中对其进行的更改将不会影响它,因为if __name__ == "__main__"块赢了不在子进程中执行.f直接在其模块中使用该类,因此效果基本相同.
x显示不同值的原因略有不同.您的f函数将从模块中打印全局变量x.在您的main()函数中,您有另一个局部变量x,因此x = 1此处的设置不会影响x两个进程中的模块级别.它被传递给g作为参数,因此在这种情况下,它将使alays具有本地值1.
| 归档时间: |
|
| 查看次数: |
3672 次 |
| 最近记录: |