试图理解Python MRO,但对其解析顺序感到困惑

2024-04-20 11:42:58 发布

您现在位置:Python中文网/ 问答频道 /正文

所以我试图理解MRO是如何工作的,但我无法理解它的某些部分,我理解解释器从左到右选择特殊性而不是泛型,如果是这样,那么这是如何发生的

class X:
    pass

class Y:
    pass

class Z:
    pass

class w:
    pass

class A(X, Y):
    pass

class B(w, Z):
    pass

class D(X, w):
    pass

class M(D, A, B, Z):
    pass


print(M.mro())

# Output
# [<class '__main__.M'>, <class '__main__.D'>, <class '__main__.A'>, <class '__main__.X'>,
#  <class '__main__.Y'>, <class '__main__.B'>, <class '__main__.w'>, <class '__main__.Z'>, 
# <class 'object'>]

还是这个

class X:
    pass


class Y:
    pass


class Z:
    pass


class A(X, Y):
    pass


class B(Y, Z):
    pass


class M(B, A, Z):
    pass

# Output:
# [<class '__main__.M'>, <class '__main__.B'>,
#  <class '__main__.A'>, <class '__main__.X'>,
#  <class '__main__.Y'>, <class '__main__.Z'>,
#  <class 'object'>]

print(M.mro())

有人能帮我理解解析顺序吗?因为在我看来,每次继承级别变得更复杂时,规则都是相互矛盾的


1条回答
网友
1楼 · 发布于 2024-04-20 11:42:58

MRO遵循两条简单规则:

  1. 在MRO中,每个类都在其祖先之前
  2. 如果一个类有多个父类,则父类将按顺序(但不一定连续)出现在MRO中

考虑^ {CD1>}。根据规则1,M必须出现在BAZ之前。根据规则2,B必须在A之前,并且A必须在Z之前

请注意,并不总是能够找到符合这些规则的MRO,在这种情况下,您会立即得到一个错误:

>>> class X: pass
...
>>> class Y: pass
...
>>> class A(X, Y): pass
...
>>> class B(Y, X): pass
...
>>> class C(A, B): pass
...
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: Cannot create a consistent method resolution
order (MRO) for bases X, Y

AB都很好,但没有发现C的MRO。在C的MRO中,X必须在Y之前,因为C继承自A。但是因为C也继承自B,所以Y必须在X之前。没有满足这两个约束的排序

相关问题 更多 >