Python Call Parent Method Multiple Inheritance
10,477
Solution 1
You can use __bases__ like this
class D(A, B, C):
def foo(self):
print("foo from D")
for cls in D.__bases__:
cls().foo("D")
With this change, the output will be
foo from D
foo from A, call from D
foo from B, call from D
foo from C, call from D
Solution 2
Add super() call's in other classes as well except C. Since D's MRO is
>>> D.__mro__
(<class '__main__.D'>, <class '__main__.A'>, <class '__main__.B'>, <class '__main__.C'>, <type 'object'>)
You don't need super call in C.
Code:
class A(object):
def foo(self, call_from):
print "foo from A, call from %s" % call_from
super(A,self).foo('A')
class B(object):
def foo(self, call_from):
print "foo from B, call from %s" % call_from
super(B, self).foo('B')
class C(object):
def foo(self, call_from):
print "foo from C, call from %s" % call_from
class D(A, B, C):
def foo(self):
print "foo from D"
super(D, self).foo("D")
d = D()
d.foo()
Output:
foo from D
foo from A, call from D
foo from B, call from A
foo from C, call from B
Related videos on Youtube
Author by
Edwin Lunando
Updated on June 09, 2022Comments
-
Edwin Lunando 7 monthsSo, i have a situation like this.
class A(object): def foo(self, call_from): print "foo from A, call from %s" % call_from class B(object): def foo(self, call_from): print "foo from B, call from %s" % call_from class C(object): def foo(self, call_from): print "foo from C, call from %s" % call_from class D(A, B, C): def foo(self): print "foo from D" super(D, self).foo("D") d = D() d.foo()The result of the code is
foo from D foo from A, call from DI want to call all parent method, in this case, foo method, from
Dclass without using super at the parent class likeA. I just want to call the super from theDclass. TheA,B, andCclass is just like mixin class and I want to call all foo method fromD. How can i achieve this? -
Edwin Lunando about 9 yearsIn case you do not understand my description, I want to call allfoomethod without calling super at the parent class likeAorBorC. -
mgilson about 9 years@EdwinLunando -- I believe that's just not how it goes. In order for super to work properly, all the classes need to use it. see the section on mixing super methods with non super methods. -
Ashwini Chaudhary about 9 years@EdwinLunando Then iterate over__mro__, or__bases__and call each class explicitly, but then you can't usesuperinD. -
mgilson about 9 yearsThis is a little sketchy ... What if you now have two classes which both inherit from D and then another class which inherits from both of those? Nowfoowill callA.footwice. -
mgilson about 9 yearsOr what happens ifB.foodoesn't exist? And finally, I think it should becls.foo(self), notcls().foo() -
thefourtheye about 9 years@mgilson Then, we have to usemro? And those are not class methods, right? So, I had to create objects to call them. -
mgilson about 9 yearsThey're not class methods, but you can call the method from the class if you explicitly passselfas the first argument (andselfis of the correct type). -
thefourtheye about 9 yearsIn this case, we don't have a problem withself, but in his actual code, he might mutateselfand that would create problems. So, it would be better to call it this way, I believe -
Edwin Lunando about 9 yearsThis is what I need! Thank you. :D. I changed theD__bases__intoself.__class__.__bases__and it work greatly. -
interjay over 8 yearsThis solution is wrong because now callingA().foo()orB().foo()will raise an exception. You can now only use these classes from a derived class which also derives fromC(or a similar class), and the order becomes important as well (Cmust be last). To make this work correctly, you'd need all classes to be derived from a base class that implementsfoo.