python3 - super()对多继承的行为 [英] python3 - behaviour of super() on multi-inheritance
问题描述
我知道这里已经讨论过super()和多继承。但我没有找到解决方案,关于我在python3中的具体问题。
假设我们有:
I know that super() and multi-inheritance have already been discussed here. But I did not find a solution, regarding my specific problem in python3. Let's assume we have:
#! /usr/bin/env python3
class A(object):
def __init__(self):
super().__init__()
def foo(self):
print("The")
class B(object):
def __init__(self):
super().__init__()
def foo(self):
print("world")
class C(B):
def __init__(self):
super().__init__()
def foo(self):
super().foo()
print("is")
class D(A,C):
def __init__(self):
super().__init__()
def foo(self):
super().foo()
print("nice")
d = D()
d.foo()
这会让我:
The
nice
另一方面,如果我改变D中的继承顺序( )到:
On the other hand, if I change the order of inheritance in D() to:
class D(C,A):
def __init__(self):
super().__init__()
def foo(self):
super().foo()
print("nice")
它给了我
world
is
nice
然而,我只获得所需的输出:
I, however, only get the desired output:
The
world
is
nice
使用:
class D(C,A):
def __init__(self):
super().__init__()
def foo(self):
A.foo(self)
C.foo(self)
print("nice")
我发现它非常不优雅。
所以我的问题是:是否可以在python3中使用super()来调用两个超类的超级方法而不仅仅是第一个?
So my question is: Is it possible to use super() in python3 invoking the super method of both super classes instead of just the first?
推荐答案
不幸的是,如果不知道 D
的方法解析顺序(MRO),就无法调用 super()
在 D
中获取两个基类。
Unfortunately, without a knowledge of the method resolution order (MRO) of D
, there is no way to call super()
in D
to get at both base classes.
但是MRO是一个强大的概念。在第二种情况下,
But the MRO is powerful concept. In the second case,
class D(C,A):
...
(MRO)
>>> D.mro()
[<class '__main__.D'>, <class '__main__.C'>, <class '__main__.B'>, <class '__main__.A'>, <class 'object'>]
因为调用 super()
将您带到MRO的下一个班级,正如Pieters先生所说,并且您希望打印语句的顺序为 A
, B
, C
,然后 D
,只需在<$ c的每个定义中首先放置 super()。foo()
并且 print(...)
秒$ C> FOO()。唯一的例外是不要在类 A
中放入 super()。foo()
,因为 foo()
未在对象
中定义。
Inasmuch as calling super()
takes you to the next class in the MRO, as Mr. Pieters stated, and you want the print statements coming in the order of A
, B
, C
, then D
, simply put super().foo()
first and print(...)
second in each definition of foo()
. The only exception is do not put super().foo()
in class A
because foo()
is not defined in object
.
#! /usr/bin/env python3
class A(object):
def __init__(self):
super().__init__()
def foo(self):
print("The")
class B(object):
def __init__(self):
super().__init__()
def foo(self):
super().foo() # Inserted
print("world")
class C(B):
def __init__(self):
super().__init__()
def foo(self):
super().foo()
print("is")
class D(C,A): # Correct ordering
def __init__(self):
super().__init__()
def foo(self):
super().foo()
print("nice")
d = D()
d.foo()
替代解决方案
第一种情况下的 D(A,C)
的MRO也包括所有类,所以正确排序 super()
和 print(...)
声明s,一个可以使它工作:
Alternate solution
The MRO of D(A,C)
in the first case includes all classes as well, so with correct ordering of super()
and print(...)
statements, one can make it work:
class A(object):
def foo(self):
print("The")
super().foo()
class B(object):
def foo(self):
print("world")
class C(B):
def foo(self):
super().foo()
print("is")
class D(A,C):
def foo(self):
super().foo()
print("nice")
D().foo()
进一步阅读
了解继承顺序(例如 D类(C,A)
或 D类(A,C)
)和MRO,见 https://www.python.org/download/releases/2.3/mro/ 。详细描述了C3方法的分辨率顺序,并且有很好的绘制的ASCII类层次结构,标有MRO。
Further reading
To understand inheritance order (e.g. class D(C,A)
or class D(A,C)
) and MRO, see https://www.python.org/download/releases/2.3/mro/. The C3 method resolution order is described in detail and there are nicely drawn ASCII class hierarchies with the MRO labeled.
这篇关于python3 - super()对多继承的行为的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!