31

在 Python 中,是否可以从 Bar 自身中获取包含另一个对象 Bar 的对象,比如 Foo?这是我的意思的一个例子

class Foo(object):
    def __init__(self):
        self.bar = Bar()
        self.text = "Hello World"

class Bar(object):
    def __init__(self):
        self.newText = foo.text #This is what I want to do, 
                                #access the properties of the container object

foo = Foo()

这可能吗?谢谢!

4

5 回答 5

49

传递对 Bar 对象的引用,如下所示:

class Foo(object):
    def __init__(self):
        self.text = "Hello World"  # has to be created first, so Bar.__init__ can reference it
        self.bar = Bar(self)

class Bar(object):
    def __init__(self, parent):
        self.parent = parent
        self.newText = parent.text

foo = Foo()

编辑:正如@thomleo 所指出的,这可能会导致垃圾收集出现问题。建议的解决方案在http://eli.thegreenplace.net/2009/06/12/safely-using-destructors-in-python/中列出,看起来像

import weakref

class Foo(object):
    def __init__(self):
        self.text = "Hello World"
        self.bar = Bar(self)

class Bar(object):
    def __init__(self, parent):
        self.parent = weakref.ref(parent)    # <= garbage-collector safe!
        self.newText = parent.text

foo = Foo()
于 2012-05-28T23:56:42.917 回答
5

是否有可能从 Bar 本身中获取包含另一个对象 Bar 的对象,比如 Foo?

不是“自动”,因为语言不是那样构建的,特别是语言的构建使得无法保证 Foo 存在。

也就是说,你总是可以明确地做到这一点。属性,就像 Python 中的所有其他标识符一样,只是名称,而不是数据的存储空间;所以没有什么能阻止您让 Bar 实例具有手动分配的foo属性,即 Foo 实例,反之亦然。

于 2012-05-29T00:00:08.583 回答
2

是的,这是可能的。即使没有在对象创建时传递容器引用,即如果您的对象是类属性。您的对象需要实现描述符协议(有一个__get__()):

class ChildName(SimpleNamespace):                                                         

    def __get__(self, instance, owner):
        # instance is our parent
        return f'I am {self.name}, my parent is {instance.name}.'


class ChildDiff(SimpleNamespace):

    @property
    def diff(self):
        return self.born - self.parent.born

    def age_diff(self):
        return f'I am {self.diff} years older than {self.parent.name}.'

    def __get__(self, instance, owner):
        self.parent = instance  # XXX: weakref?
        return self  # expose object to be able call age_diff() etc.


class Parent(SimpleNamespace):

    child_name = ChildName(name='Bar')
    child_diff = ChildDiff(born=42)


parent = Parent(name='Foo', born=23)
print(parent.child_name)             # ... I am Bar, my parent is Foo.
print(parent.child_diff.age_diff())  # ... I am 19 years older than Foo.
于 2019-07-09T11:05:35.313 回答
0

这对我有用:

父母

import child

obj_1  = 25             # an object that both parent and child can access

def startup():          # any startup function
    global obj_1
    child.ref( obj_1 )  # send the shared object to the child
    ...

孩子

obj_1 = 0               # initual value will be overwritten

def ref(shared_obj):    # receive a reference to the shared object
    global  obj_1       # shared object is global in the child, optional
    obj_1 = shared_obj  # set obj_1 in the child to be obj_1 in the parent
于 2021-12-18T02:48:30.300 回答
-3

如何使用继承:

class Bar(object):
    def __init__(self):
        self.newText = self.text

class Foo(Bar):
    def __init__(self):
        self.txt = 'Hello World'
        Bar.__init__(self)

foo = Foo()
print foo.newText
于 2012-05-29T00:35:18.063 回答