我在玩弄 python 中的多重继承,遇到了一个我无法理解它是如何发生的情况。
这是继承布局:
A F
/ \ |
B C |
\ | /
\ | /
D
大家耳熟能详的ABCD钻石。 再加上一个额外的“F”类,我把它扔进去是为了好玩。
代码如下:
class A(object):
def foo(self, call_from):
print "foo from A, call from %s" % call_from
super(A, self).foo("A")
class B(A):
def foo(self, call_from):
print "foo from B, call from %s" % call_from
super(B, self).foo("B")
class C(A):
def foo(self, call_from):
print "foo from C, call from %s" % call_from
super(C, self).foo("C")
class F(object):
def foo(self, call_from):
print "foo from F, call from %s" % call_from
class D(B, C, F):
def foo(self):
print "foo from D"
super(D, self).foo("D")
输出:
>>> d = D()
>>> d.foo()
foo from D
foo from B, call from D
foo from C, call from B
foo from A, call from C
foo from F, call from A
方法解析顺序:
>>> D.__mro__
(<class '__main__.D'>, <class '__main__.B'>, <class '__main__.C'>, <class '__main__.A'>, <class '__main__.F'>, <type 'object'>)
foo from C, call from B
而不是foo from C, call from D
来自 F 的 foo,来自 A 的调用
只是让我失望...
似乎 super()
是按照方法解析顺序链接起来的,忽略了类之间的关系,但我不确定。
有人可以指出正确的方向来理解这种行为吗?
请记住,我正在尝试理解语言本身。不是试图解决实际问题。所以我没有这个用例。但如果有人能指出一个用例,那就太好了:)
UPDATE:
To summarize - super() simply let you know what is next to call base on the mro. It is not necessary the parent. While mro built base on the inheritance hierarchy, mro itself is not the inheritance hierarchy.
最佳答案
super()
的重点是遵循方法解析顺序。这就是为什么你告诉它你自己的类(class),而不是你的父类(class)。程序员很难预测接下来将调用哪个类,因此您让 super()
来处理它。
您已经从 D 调用了 B,那么您如何才能从 D 调用 C? D.foo() 只能调用另一个 foo(),因为那里只有一个函数调用。这将是一个线性调用链,因此类必须线性化,这就是方法解析顺序所做的。
关于python - super 迷惑的python多重继承super(),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11354786/