python 个进程创建 class 个相同的实例

python processes create same instance of class

我有一个使用 multiprocessing 库的 python 应用程序,我 运行 遇到了一个问题,我希望不同的进程创建 [=27= 的不同实例],但是,它们实际上是在创建 class 的相同实例。举个例子:

from multiprocessing import Process
from time import sleep


class Foo:
    name = None


def get_foobar():
    return Foo()


class MyProcess(Process):
    def run(self):
        print('process {} running in pid {}'.format(self.name, self.pid))
        my_foo = get_foobar()
        print('got foo {}'.format(id(my_foo)))

        if my_foo.name is None:
            my_foo.name = self.name.upper()

        print("foo's name is {}".format(my_foo.name))

        # do some work
        sleep(3)

        print('process {} running in pid {} done'.format(self.name, self.pid))


for _ in range(2):
    p = MyProcess()
    p.start()

我得到以下输出:

process MyProcess-1 running in pid 65975
got foo 4322815784
foo's name is MYPROCESS-1
process MyProcess-2 running in pid 65976
got foo 4322815784
foo's name is MYPROCESS-2
process MyProcess-1 running in pid 65975 done
process MyProcess-2 running in pid 65976 done

我原以为第二个进程会有一个不同的 class 实例。 get_foobar() 如何能够 return 每个进程的 Foo 相同实例?

编辑/更新: 我是 运行 在 OSX 和 Ubuntu 上的 python 3.5。

基本上你的答案在这里:Why is the id of a Python class not unique when called quickly?

最相关的引用是:

The id of an object is only guaranteed to be unique during that object's lifetime, not over the entire lifetime of a program.

您的第一个 Foo() 实例似乎刚好 "dies" 在创建第二个实例之前,因此它们最终可能会获得相同的 ID。

没有多处理也会发生同样的事情:

>>> def run():
...     my_foo = get_foobar()
...     print('got foo {}'.format(id(my_foo))) ... 
>>> run() 
got foo 140690243732040
>>> run() 
got foo 140690243732040

编辑:这是来自 docs:

Return the “identity” of an object. This is an integer which is guaranteed to be unique and constant for this object during its lifetime. Two objects with non-overlapping lifetimes may have the same id() value.

在这种情况下,对象仅存在于特定范围内(即 run 函数)可能意味着它们无论如何都具有不同的生命周期。这与 python 2 文档没有什么不同,但我的猜测是实现不同,因此解释了结果。