1

This seems very confusing to me. Could someone explain why this unknown magical things happening ?

class A(object): def testA(self): print "TestA of A" self.testB() def testB(self): print "TestB of A" class B(A): def testA(self): super(B, self).testA() print "TestA of B" self.testB() def testB(self): print "TestB of B" if __name__ == '__main__': test = B() test.testA() 
 Program Output: =============== TestA of A TestB of B --> Why it is calling derived class method ? TestA of B TestB of B Expected Output: ================ TestA of A TestB of A -- I want to see A here. TestA of B TestB of B 

Your answer will be appreciated. Thank You.

1 Answer 1

2

In A.testA, you call self.testB. This means to call the "leaf" definition of testB for the current instance. Since self is an instance of testB, it calls B.testB.

Even though you wrote self.testB inside a method defined on class A, that does not mean it will call the version of the method defined on class A. You are calling the method on the instance, and at runtime the class of the instance is determined dynamically, and whatever method is defined on the instance is what will get run. Since the instance is of class B, and class B overrides testA, the instance's version of testA is the one provided by B.

If in A.testA you want to call A.testB, you have to do that explicitly by calling A.testB(self). However, you should think about why you want to do that. The whole point of overriding methods is so that you can change how a class does things. A should not need to know which version of testB is called. It should just need to know that it is calling a method called testB that does whatever the method testB is documented to do in your program/library. If A specifically requires that its own testB method be called, this makes it difficult for subclasses to alter the behavior of testB, because A will ignore their overrides and keep calling its own version instead.

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

3 Comments

Thank You. Is there any resolution of this problem ? I mean how to call the "testB()" of base class in this situation ?
@user968677: I added some more to my answer. However, you should think carefully before doing that, because if you do that you will introduce un-overridable behavior into your class, which works against the whole concept of overriding methods to change behavior.
Ah! Now I understand. Perhaps I forgot about the overriding behavior. I will create different local method for each of them for calling its own version. Thank You.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.