Python 繼承順序

2021-09-29 19:07:42 字數 1508 閱讀 9215

class base:

def __init__(self):

print('base.__init__')

class a(base):

def __init__(self):

super().__init__()

print('a.__init__')

class b(base):

def __init__(self):

super().__init__()

print('b.__init__')

class c(a,b):

def __init__(self):

super().__init__() # only one call to super() here

print('c.__init__')

執行c = c()會輸出什麼?

>>> c = c()

base.__init__

b.__init__

a.__init__

c.__init__

>>>

按照mro列表順序繼承,就理解了。

>>> c.__mro__

(, , ,

, )

「super() 有個令人吃驚的地方是它並不一定去查詢某個類在mro中下乙個直接父類」

class a:

def spam(self):

print('a.spam')

super().spam()

如果你試著直接使用這個類就會出錯:

>>> a = a()

>>> a.spam()

a.spam

traceback (most recent call last):

file "", line 1, in file "", line 4, in spam

attributeerror: 'super' object has no attribute 'spam'

>>>

但是,如果你使用多繼承的話看看會發生什麼:

>>> class b:

... def spam(self):

... print('b.spam')

...>>> class c(a,b):

... pass

...>>> c = c()

>>> c.spam()

a.spam

b.spam

>>>

你可以看到在類a中使用 super().spam() 實際上呼叫的是跟類a毫無關係的類b中的 spam() 方法。 這個用類c的mro列表就可以完全解釋清楚了:

>>> c.__mro__

(, , ,

)>>>

參考:

python繼承順序

python和c 一樣,支援多繼承。概念雖然容易,但是困難的工作是如果子類呼叫乙個自身沒有定義的屬性,它是按照何種順序去到父類尋找呢,尤其是眾多父類中有多個都包含該同名屬性。class p1 object def foo self print p1 foo class p2 object def f...

python 之 多繼承的順序

python 支援多繼承,但對與經典類和新式類來說,多繼承查詢的順序是不一樣的。經典類 新式類 classp1 deffoo self print p1 foo class p2 deffoo self print p2 foo defbar self print p2 bar class c1 p...

Python 多繼承中MRO順序

在python3 裡面,使用super當有多繼承的情況出現的時候,有時候會出現呼叫父類init呼叫不到,因為在python3 裡面有乙個預設來處理類之間呼叫順序的c3 演算法,c3用來保證每個類只呼叫一次的演算法,所有通過super 來進行呼叫的時候都會根據裡面的順序來進行呼叫 在類中可以通過 cl...