Python:在多重继承中呼叫多个init

时间:2019-02-17 01:43:04

标签: python python-3.x oop python-2.x multiple-inheritance

我有2个类:A(需要1个参数来初始化)和B(需要2个参数来初始化),以及第三个类C,它从A和B派生。

class A:
    def __init__(self, sval): 
        print("A: rcd value: ", sval)
        self.aval = sval

class B: 
    def __init__(self, sval, tval):
        print("B: rcd 2 values: ", sval, tval)
        self.aval=sval
        self.bval=tval

class C(A,B):
    def __init__(self, a, b, c):
        super().__init__(a) 
        super().__init__(b,c) # error here

c = C(1,2,3)

当我运行上面的代码时,最后一行有错误;称为A类的__init__,而不是B类的。

A: rcd value:  1
Traceback (most recent call last):
  File "inheritance.py", line 20, in <module>
    c = C(1,2,3)
  File "inheritance.py", line 16, in __init__
    super().__init__(b,c) 
TypeError: __init__() takes 2 positional arguments but 3 were given

如何从类C的__init__调用A和B的__init__函数?

编辑:我将在Debian Linux上使用Python 3.5.3,尽管我更喜欢在Python2和Python3上均可使用的解决方案。

2 个答案:

答案 0 :(得分:1)

致电A.__init__()B.__init__()而不是super().__init__()

class C(A,B):
    def __init__(self, a, b, c):
        A.__init__(self, a) 
        B.__init__(self, b, c)

Python 3(https://repl.it/repls/CooperativeTransparentRobot):

class A:
    def __init__(self, sval): 
        print("A: rcd value: ", sval)
        self.aval = sval

class B: 
    def __init__(self, sval, tval):
        print("B: rcd 2 values: ", sval, tval)
        self.aval=sval
        self.bval=tval

class C(A,B):
    def __init__(self, a, b, c):
        A.__init__(self, a) 
        B.__init__(self, b,c) # this does not give error

c = C(1,2,3)

>> Python 3.6.1 (default, Dec 2015, 13:05:11)
>> [GCC 4.8.2] on linux
>> A: rcd value:  1
>> B: rcd 2 values:  2 3

也可以在Python 2中使用: https://repl.it/repls/GreenAbleBlockchain

答案 1 :(得分:1)

让我们假设您拥有AB的控制权,可以避免在两者中使用相同的属性名称。然后,为了正确使用super,请按以下说明进行定义。

class A:
    def __init__(self, aval, **kwargs): 
        print("A: rcd value: ", aval)
        self.aval = sval
        super().__init__(**kwargs)

class B: 
    def __init__(self, b1val, b2val, **kwargs):
        print("B: rcd 2 values: ", b1val, b2val)
        self.b1val = b1val
        self.b2val = b2val
        super().__init__(**kwargs)

然后C.__init__仅需一次呼叫super

class C(A, B):
    def __init__(self, aval, b1val, b2val, **kwargs):
        super().__init__(aval=aval, b1val=b1val, b2val=b2val, **kwargs)

c = C(1, 2, 3)