理解Python类实例化

时间:2018-04-07 20:50:33

标签: python subclass

试图找出本身是类的类属性的类继承。这就是我要做的事情:

class foo:
    hello = None
    world = None

    def __init__(self, **kwargs):
        for k,v in kwargs.items():
            if hasattr(self, k):
                setattr(self, k, v)
            else:
                raise AttributeError(f'class foo has no attribute {k}')


class foo2:
    hi = None
    earth = None

    def __init__(self, **kwargs):
        for k,v in kwargs.items():
            if hasattr(self, k):
                setattr(self, k, v)
            else:
                raise AttributeError(f'class foo has no attribute {k}')

class bar:
    foo_attr = foo(hello=1, world=2)
    foo2_attr = foo2(hi=3, earth=4)


class bar2(bar):
    def __init__(self):
    super().__init__()

所以我有2个基类(foo and foo2),每个基类有2个属性(分别为hello& worldhiearth

我有另一个基类(bar),里面有类属性,包含foofoo2的默认值。

更新(包含问题):

最后,我有bar2,它是bar的子类。如何更改自身类的子类属性的值? (比如bar2中foo_attr的hello属性)

我试图为bar设置一个默认值,但我希望能够在子类化时为bar中的每个类属性设置不同的属性。这样,我可以像这样创建一堆bar的子类:

一个bar2,默认属性除了foo2.earth,我设置为20.这意味着bar2有:

  • foo.hello = 1
  • foo.world = 2
  • foo2.hi = 3
  • foo2.earth = 20

然后仍然可以创建一个bar3,假设foo()和foo2()的默认属性除了foo.hello,我可能想要设置为30然后添加一个新的属性say&#34 ;哎呀"

我该怎么做?

2 个答案:

答案 0 :(得分:0)

看起来您想为barbar2创建一个显式构造函数,以便您可以选择属性:

class bar:
    def __init__(self, hello=1, world=2, hi=3, earth=4)
        self.foo_attr = foo(hello=hello, world=world)
        self.foo2_attr = foo2(hi=hi, earth=earth)

class bar2:
    def __init__(self)
        bar.__init__(self, earth=20)

您仍然可以在新类中添加新属性。

答案 1 :(得分:0)

我认为您需要将功能放入foofoo2,如果这些功能继承自具有该功能的公共超类,则您的重复次数会减少。下面的脚本可以工作(我必须删除' f'字符串,因为我已经陷入了蟒蛇3.5的黑暗时代)。仍然有一些工作实现了bar子类,但相对合理。

import copy

class Fooinator:

    def __init__(self, **kwargs):
        badniks = self._update_instance(**kwargs)
        if badniks:
            raise AttributeError('class foo has no attributes {}'.format(badniks))

    def _update_instance(self, **kwargs):
        """Update self for variables defined at the class level returning
        names of variables not used by this class. """
        badniks = []
        for k,v in kwargs.items():
            if hasattr(self, k):
                setattr(self, k, v)
            else:
                badniks.append(k)
        return badniks

    def opt_clone(self, **kwargs):
        """Given keyword arguments, clone a copy of self if any of them are
        used by this class, else return self."""
        for k in kwargs:
            if hasattr(self, k):
                me_2 = copy.copy(self)
                me_2._update_instance(**kwargs)
                return me_2
        return self


class foo(Fooinator):
    hello = None
    world = None


class foo2(Fooinator):
    hi = None
    earth = None


class bar:
    foo_attr = foo(hello=1, world=2)
    foo2_attr = foo2(hi=3, earth=4)


class bar2(bar):
    foo2_attr = bar.foo2_attr.opt_clone(earth=20)

b = bar2()
print(b.foo_attr.hello, b.foo_attr.world, b.foo2_attr.hi, b.foo2_attr.earth)