Python多重繼承排序原理(MRO演算法解析,拓撲排序,C3演算法)
Python內建屬性MRO演算法解析
什麼是MRO
MRO(Method Resolution Order):方法解析順序。
Python語言包含了很多優秀的特性,其中多重繼承就是其中之一,但是多重繼承會引發很多問題,比如二義性,Python中一切皆引用,這使得他不會像C++一樣使用虛基類處理基類物件重複的問題,但是如果父類存在同名函式的時候還是會產生二義性,Python中處理這種問題的方法就是MRO。
對於MRO的歷史問題這個帖子說的非常詳細,但是後面說到C3演算法的時候說錯了。從評論中可以看出來。
python內建屬性MRO 請不要看這個地方。

請不要看這個地方
這文章有點瑕疵,因為按照他的思路這個地方就不對了。

研究了一晚上才梳理了所有細節。聽我慢慢道來。
在箭頭之前的你都可以看一下,寫的非常好。等你看到這個的時候,你需要了解什麼是 拓撲排序拓撲排序
瞭解這一部分的可以跳到下面去。
重點:一個圖的拓撲排序是可以有多個的!!!!
經典實現演算法:
- kahn演算法
- 基於DFS的拓撲排序
很多情況下,拓撲排序問題往往會出現在一些中等複雜程度的計算系統中。這方面最典型的例子莫過於軟體安裝了,現在大多數作業系統都至少會有一個自動安裝軟體元件的系統(Ubuntu Linux 系統中的 apt-get,CentOS Linux 系統中的 RPM,Mac OS X 系統中的 brew 等),這些系統會自動檢測依賴關係中缺少的部分,並下載安裝它們,對於這一類工作,相關元件就必須按照一定的拓撲順序來安裝。
Kahn演算法:
摘一段維基百科上關於Kahn演算法的偽碼描述:
L← Empty list that will contain the sorted elements S ← Set of all nodes with no incoming edges while S is non-empty do remove a node n from S insert n into L foreach node m with an edge e from nto m do remove edge e from thegraph ifm has no other incoming edges then insert m into S if graph has edges then return error (graph has at least onecycle) else return L (a topologically sortedorder)
思想很簡單,首先用鄰接表來構建一個圖。然後用一個臨界表來記錄每個頂點的入度,再用一個表來加入入度為0的點。最後一次輸出。(什麼是入度?a入度為0代表沒有點能指向a,為1就是又一個點能指向a)
方法如下:
- 首先初始化一個表存放著這個圖入度為0的點S。
- 從這個表裡面取資料(如果這個表是棧,就是先進後出的取,如果是佇列,就是先進先取。從這可以看出為什麼拓撲排序為什麼不唯一。),將該頂點放入List中。
- 通過迴圈遍歷由上面去出的頂點引出的所有邊,同時獲取該邊的另外一個頂點,如果改頂點的入度在減去本條邊之後為0,那麼就把這個頂點放到S的集合中,然後繼續重複2的動作。
- 當集合為空之後,檢查圖中是否還存在任何邊,如果存在的話,說明圖中存在環路。不存在,返回結果List,此List中的順序就是拓撲排序的結果。

我總覺得按照連結中樓主的思路,紅色的地方是有錯誤的。誰能私聊我討論討論。
複雜度分析:
初始化入度為0的集合需要遍歷整張圖,檢查每個節點和每條邊,因此複雜度為O(E+V);
然後對該集合進行操作,又需要遍歷整張圖中的,每條邊,複雜度也為O(E+V);
因此Kahn演算法的複雜度即為O(E+V)。
C3演算法

箭頭是核心,懂這一塊,應該就沒有問題來。