MRO

发布时间 2023-07-19 22:56:35作者: Allen_Hao

MRO(Method Resolution Order)是指多继承中确定方法调用顺序的算法。Python 3 默认使用 C3 算法来计算 MRO。

在使用多继承时,以下是一些 MRO 的最佳实践、坑和示例:

最佳实践:

  1. 明确继承关系:在设计类的继承结构时,要清晰明确地指定父类和子类之间的继承关系,避免混乱或歧义。
  2. 使用super():在重写父类方法时,可以使用 super() 函数来调用父类的方法。这样可以确保方法按照正确的 MRO 被调用,并且能够避免冲突和循环调用。
  3. 理解MRO算法:了解 C3 算法以及 MRO 的计算规则,可以帮助理解多继承的调用顺序,避免意外行为。

常见坑:

  1. 方法冲突:当不同的父类中存在相同名称的方法时,如果没有明确指定调用哪个父类的方法,可能会导致意外的结果。可以使用重命名、调整继承顺序或使用 super() 来解决这个问题。
  2. 菱形继承问题:当一个子类同时继承自两个或更多个具有共同父类的类时,可能会出现菱形继承问题。这时需要确保继承结构合理并使用正确的 MRO 算法。

 

 1 '''
 2 MRO(Method Resolution Order)是指多继承中确定方法调用顺序的算法。Python 3 默认使用 C3 算法来计算 MRO。
 3 
 4 在使用多继承时,以下是一些 MRO 的最佳实践、坑和示例:
 5 
 6 最佳实践:
 7     1. 明确继承关系:在设计类的继承结构时,要清晰明确地指定父类和子类之间的继承关系,避免混乱或歧义。
 8     2. 使用super():在重写父类方法时,可以使用 super() 函数来调用父类的方法。这样可以确保方法按照正确的 MRO 被调用,并且能够避免冲突和循环调用。
 9     3. 理解MRO算法:了解 C3 算法以及 MRO 的计算规则,可以帮助理解多继承的调用顺序,避免意外行为。
10 
11 常见坑:
12     1. 方法冲突:当不同的父类中存在相同名称的方法时,如果没有明确指定调用哪个父类的方法,可能会导致意外的结果。可以使用重命名、调整继承顺序或使用 super() 来解决这个问题。
13     2. 菱形继承问题:当一个子类同时继承自两个或更多个具有共同父类的类时,可能会出现菱形继承问题。这时需要确保继承结构合理并使用正确的 MRO 算法。
14 '''
15 
16 
17 class A:
18     def say_hello(self):
19         print("Hello from A")
20 
21 
22 class B(A):
23     def say_hello(self):
24         print("Hello from B")
25         super().say_hello()
26 
27 
28 class C(A):
29     def say_hello(self):
30         print("Hello from C")
31         super().say_hello()
32 
33 
34 class D(B, C):
35     def say_hello(self):
36         print("Hello from D")
37         super().say_hello()
38 
39 
40 d = D()
41 d.say_hello()
42 
43 # 输出结果:
44 # Hello from D
45 # Hello from B
46 # Hello from C
47 # Hello from A

在上述示例中,类 D 继承自类 BC,它们又都继承自类 A。当调用 d.say_hello() 时,按照 MRO 的顺序,先调用 Dsay_hello() 方法,然后调用 Bsay_hello() 方法,并调用 Csay_hello() 方法,最后调用 Asay_hello() 方法。

通过使用 super() 函数,可以确保方法按照正确的 MRO 被调用,实现了多继承的协作和顺序调用。

总之,在使用多继承时,理解 MRO 算法、明确继承关系和使用 super() 函数是避免问题、提高代码可读性和维护性的关键。

如果把D类的方法删除即

1 class D(B, C):
2     pass
3     # def say_hello(self):
4     #     print("Hello from D")
5     #     super().say_hello()

输出:

Hello from B
Hello from C
Hello from A