學習筆記(Python繼承) 有幾種叫法(父類-子類、基類-派生類)先拿代碼演示一下: 1 class father: 2 def work(self): 3 print("work>>>>>") 4 5 def car(self): 6 print("car>>>>>>>>>") 7 8 clas ...
學習筆記(Python繼承)
有幾種叫法(父類-子類、基類-派生類)
先拿代碼演示一下:
1 class father: 2 def work(self): 3 print("work>>>>>") 4 5 def car(self): 6 print("car>>>>>>>>>") 7 8 class son(father): #想要繼承就得添加父類 9 def study(self): 10 print("study>>>>>>>>>>") 11 12 obj = son() 13 obj.work() #在上面方法中,work中的self是形參,此時指向的是obj 14 #除此之外還很重要的是,self永遠指向調用方法的調用者(比如這裡指向obj) 15 #work>>>>>
由上述代碼可以看出此時obj是調用子類的對象,但是卻可以使用父類的方法,其主要原因是子類後添加了父類,如果沒有加父類,則調用不了父類的方法從而報錯,這種形式叫做繼承
(self 永遠指向調用方法的調用者)
1、當繼承父類的方法時,如果不想調用父類的某些方法,則就需要自己在子類中重寫
(下麵類中重寫父類中的work方法,先別去想太多限制)
1 class son(father): 2 def study(self): 3 print("study>>>>>>>>>>") 4 5 def work(self): 6 print("s.work") #不想繼承就自己寫(重寫) 7 8 #此時在調用方法時,先從子類的方法中查找,如果有該方法則先調用,沒有的話就去父類中調用 9 obj = son() 10 obj.work() #s.work
2、當繼承父類方法時,自己子類重寫了但是還是想要去執行父類被重寫的方法,則進行下麵操作:
1 def work(self): 2 print("s.work") 3 super(son,self).work() #方一:調用super方法,super(當前類的名,self).父類被重寫的方法()) 4 father.work(self) #方二:這種方法是主動調用父類方法,此時的self需要我們主動添加,表示父類也要執行其對象方法
3、python和C++一樣可以繼承多個父類
1 class uncle: 2 def video(self): 3 print("uncle.video") 4 class father(uncle): 5 def work(self): 6 print("father.work") 7 class mother: 8 def car(self): 9 print("mother.car") 10 11 class son(father,mother): 12 def study(self): 13 print("son.study")
(1)多個父類繼承是從左到右開始繼承:
obj = son() obj.car() # mother.car
(此時是先在father類中找car()方法,沒有則再跳轉到mother類中)
(2)如果繼承的父類之上還有父類,則“一直尋找到底”,有則調用,無則繼承下一個父類去找尋方法
obj = son() obj.video() # uncle.video
(3)上面兩種說法是基於其最終父類不是指向同一個,而現在的第三種判斷則是基於最終父類是同一個的情況下而進行的討論,代碼如下:
class aunt: def computer(self): print("aunt.computer") class uncle: def video(self): print("uncle.video") class father(uncle): def work(self): print("father.work") class mother(aunt): def car(self): print("mother.car") class son(father, mother): def study(self): print("son.study") obj = son() obj.computer() #aunt.computer
其執行的順序如下圖:
紅線是往上繼承,黑線是代碼執行的流程
還是跟(1)(2)差不多,但是不一樣的是,在左側一直未找到所調用的方法時,並沒有有一直找到底,而是在最後一個父類前回到son子類,開始在mother類中尋找,最後才指向aunt類並找到其computer()方法
((3)總結:如果有共同父類,則在尋找方法時,不會一直尋到底,而是在尋到底之前的父類換到最原始給的父類中去尋找,如果都找不到才會找尋到底父類)怎麼好理解就怎麼去記憶
(4)self.方法()使用時代碼執行的順序
(下麵代碼修改了一些)
class uncle: def video(self): print("uncle.video") class father(uncle): def work(self): print("father.work") self.car() def car(self): print("father.car") class mother: def car(self): print("mother.car") class son(mother,father): def study(self): print("son.study") obj = son() obj.work() #father.work #mother.car
對象在去父類找尋方法時,由於mother類沒有其方法,在father類下找到並執行後,方法內還有self.car(),按道理來說應該是同一類下有該方法就優先執行,但是結果卻是mother.car,其原因很簡單,當碰到self.方法()時,就應該返回到其對象(self所指向的對象,此代碼是obj)所調用的類中再去執行其方法的調用(對於上述代碼,就是再次調用obj.car(),然後先從方法的子類中尋找,再向其父類中找尋方法,第一個父類時mother,在mother類中有car()方法,所以就直接調用執行了,over!)
(5)類中的__init__()方法是在找尋到的第一個時去執行:
1 class uncle: 2 def __init__(self): 3 print("uncle.init") 4 def video(self): 5 print("uncle.video") 6 class father(uncle): 7 def __init__(self): 8 print("father.init") 9 def work(self): 10 print("father.work") 11 class mother: 12 def car(self): 13 print("mother.car") 14 15 class son(father,mother): 16 def study(self): 17 print("son.study") 18 obj = son() #father.init
(上述代碼father類還繼承了一個父類,它們同時有__init__方法,但是先遍歷到子類father,所以就先調用其類下的init方法,每當執行其類的對象時,只會執行一次最先遇到的__init__的方法)