0

So we have a code snippet below. I don't understand why it behave this way. Why does super(B, self).go() resolves to the go method of the C class?

class A(object):
    def go(self):
        print("go A go!")

class B(A):
    def go(self):
        super(B, self).go()
        print("go B go!")

class C(A):
    def go(self):
        super(C, self).go()
        print("go C go!")

class D(B, C):
    def go(self):
        super(D, self).go()
        print("go D go!")

d = D()
d.go()
# go A go!
# go C go!
# go B go!
# go D go!
1

1 Answer 1

5

Despite its name, super does not necessarily refer to a superclass. super(B, self) refers to the class in self's MRO that follows B.

You can see the MRO for D with

>>> D.__mro__
(<class '__main__.D'>, <class '__main__.B'>, <class '__main__.C'>, <class '__main__.A'>, <type 'object'>)

This means that from d.go, super(D, self) refers to B. When B.go is called as a result, super(B, self) refers to C, not A. This is because self is still an instance of D, so it is D.__mro__ that dictates what gets called next, not the static superclass of B.

The most important thing to remember about super is that inside Foo.go, you do not know what class super(Foo, self) will refer to, because you do not know if self is an instance of Foo or a descendent of Foo.

Sign up to request clarification or add additional context in comments.

1 Comment

A useful thing to note: MRO stands for "method resolution order" - literally the order in which super methods are executed. Another way to think about this is "what would you expect to happen". It seems obvious that A.go should not be called twice. So if it should be called only once, when should it be called. The answer is the MRO order.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.