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
Share:
10,477

Related videos on Youtube

Edwin Lunando
Author by

Edwin Lunando

Updated on June 09, 2022

Comments

  • Edwin Lunando
    Edwin Lunando 7 months

    So, 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 D
    

    I want to call all parent method, in this case, foo method, from D class without using super at the parent class like A. I just want to call the super from the D class. The A, B, and C class is just like mixin class and I want to call all foo method from D. How can i achieve this?

  • Edwin Lunando
    Edwin Lunando about 9 years
    In case you do not understand my description, I want to call all foo method without calling super at the parent class like A or B or C.
  • mgilson
    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
    Ashwini Chaudhary about 9 years
    @EdwinLunando Then iterate over __mro__, or __bases__ and call each class explicitly, but then you can't use super in D.
  • mgilson
    mgilson about 9 years
    This 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? Now foo will call A.foo twice.
  • mgilson
    mgilson about 9 years
    Or what happens if B.foo doesn't exist? And finally, I think it should be cls.foo(self), not cls().foo()
  • thefourtheye
    thefourtheye about 9 years
    @mgilson Then, we have to use mro? And those are not class methods, right? So, I had to create objects to call them.
  • mgilson
    mgilson about 9 years
    They're not class methods, but you can call the method from the class if you explicitly pass self as the first argument (and self is of the correct type).
  • thefourtheye
    thefourtheye about 9 years
    In this case, we don't have a problem with self, but in his actual code, he might mutate self and that would create problems. So, it would be better to call it this way, I believe
  • Edwin Lunando
    Edwin Lunando about 9 years
    This is what I need! Thank you. :D. I changed the D__bases__ into self.__class__.__bases__ and it work greatly.
  • interjay
    interjay over 8 years
    This solution is wrong because now calling A().foo() or B().foo() will raise an exception. You can now only use these classes from a derived class which also derives from C (or a similar class), and the order becomes important as well (C must be last). To make this work correctly, you'd need all classes to be derived from a base class that implements foo.

Related