簡體   English   中英

方法解析順序 MRO

[英]method resolution order MRO

為什么搜索 B 后,沒有更深入地搜索 Y OR z 而是去搜索 A?

Y 是 A 的父級,如果應該先搜索 A,但 Y 是 B 的父級,所以它應該先搜索 Y,為什么這不會拋出 MRO 錯誤?

有人可以解釋這個查找是如何工作的嗎?

class X(object):pass
class Y(object): pass
class Z(object): pass
class A(X,Y): pass
class B(Y,Z):pass
class M(B,A,Z):pass
print M.__mro__

(<class '__main__.M'>, <class '__main__.B'>, <class '__main__.A'>, <class '__main__.X'>, <class '__main__.Y'>, <class '__main__.Z'>, <type 'object'>)

在此處輸入圖片說明

在您的具體示例中,在搜索B ,我們不能立即考慮Y因為它是A的孩子。 我們不能立即考慮Z ,因為M繼承自Z之前A繼承。


Python 在此處使用 C3 方法解析順序詳細信息

C3解析順序很好的解決了鑽石繼承問題

在下面的示例中,我們有一個非常通用的類Object ,它是BC的超類。 如果BC都沒有實現,我們只希望考慮Object方法實現(比如__repr__或其他東西)。

         Object
         /   \
        B     C
         \   /
           A

換句話說,考慮了A的父類的傳遞閉包中的每個可能的父類,但是這些類是根據從基類到相關類的“最新”路徑進行排序的。

object有兩條路徑:

A -> B -> Object
A -> C -> Object

“最新”路徑是A -> C -> Object因為A -> B -> Object在左偏深度優先搜索中會更早。

C3 線性化滿足兩個關鍵不變量:

  • 如果X繼承自YX是前檢查Y
  • 如果Z從繼承U然后V的順序U之前檢查V

事實上, C3線性化保證了這兩個屬性都成立。

可以構建無法線性化的層次結構,在這種情況下,您會在類定義時收到異常。

運行inherit.py

class E: pass      
class F: pass
class A(E, F): pass
class B(F, E): pass
class Z(A, B): pass

產生以下錯誤。

Traceback (most recent call last):
  File "inherit.py", line 5, in <module>
    class Z(A, B): pass
TypeError: Cannot create a consistent method resolution
order (MRO) for bases E, F

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM