-1

this is my code:

class Circle():
    def draw()
    ....

class Rectangle():
    def draw()
    ....

class Form(Rectangle):
    ....

class NewForm(Circle, Form):
    ....

So now the draw Method of Circle overrides the draw Method of Form -> Rectangle. But if i change the position of inheritance like:

class NewForm(Form, Circle):
    ....

the draw method of Rectangle overrides the draw method of circle.

Is there a logical answer why Python is looking at the position of inheritance?

Elias
  • 125
  • 2
  • 22
  • 4
    *"Is there a logical answer why Python is looking at the position of inheritance?"* Can you clarify what you were expecting? i.e. if you don't think Python's behaviour is logical, what do you think would be logical? – slothrop Jul 01 '23 at 09:24
  • Duplicate of https://stackoverflow.com/questions/607186/how-does-pythons-super-do-the-right-thing and a few tens more SO questions... (Downvoting for "insufficient research") – STerliakov Jul 01 '23 at 09:44
  • Does this answer your question? [How does Python's "super" do the right thing?](https://stackoverflow.com/questions/607186/how-does-pythons-super-do-the-right-thing) – Security Hound Jul 02 '23 at 13:37

1 Answers1

0

In Python, the order of inheritance does indeed impact method resolution in multiple inheritance. This behavior is determined by the C3 linearization algorithm, also known as the Method Resolution Order (MRO).

The MRO is responsible for establishing the order in which methods are searched for and resolved during inheritance. It ensures that the inheritance hierarchy is traversed in a consistent and predictable manner.

In the first case, where NewForm inherits from Circle and then Form, the MRO follows a left-to-right order. This means that when a method is called on an instance of NewForm, Python first searches for the method in Circle. If it's found there, the method is executed, and the search stops. If it's not found, Python continues searching in the next class in the inheritance order, which is Form.

However, when you change the order of inheritance to Form, Circle, the MRO changes as well. Now, the MRO follows a right-to-left order. This means that when a method is called on an instance of NewForm, Python first searches for the method in Form. If it's found there, the method is executed, and the search stops. Only if it's not found in Form does Python continue searching in Circle.

This behavior is designed to respect the order of inheritance and ensures that methods are resolved consistently. It allows you to control method overriding and prioritize certain classes in the inheritance hierarchy.

Here's an example:

class Circle:
    def draw(self):
        print("Drawing a circle")

class Rectangle:
    def draw(self):
        print("Drawing a rectangle")

class Form(Rectangle):
    pass

class NewForm(Circle, Form):
    pass

# Create an instance of NewForm
new_form = NewForm()

# Method resolution order for NewForm
print(NewForm.mro())  

Ouput:

[<class '__main__.NewForm'>, <class '__main__.Circle'>, <class '__main__.Form'>, <class '__main__.Rectangle'>, <class 'object'>]

and then if we call draw method on an instance of NewForm:

new_form.draw()

Take careful notice, when we call the draw method on an instance of NewForm, it first looks for the method in Form. Since Form does not have a draw method, the search continues to Circle, and the draw method from Circle gets executed. As a result, the output will be:

Drawing a circle
Ali
  • 350
  • 3
  • 10