Python全棧開發記錄_第九篇(類的基礎_封裝_繼承_多型)
有點時間沒更新部落格了,今天就開始學習類了,今天主要是類的基礎篇,我們知道面向物件的三大特性,那就是封裝,繼承和多型。內容參考該部落格https://www.cnblogs.com/wupeiqi/p/4493506.html
之前我們寫的都是函式,可以說是面向過程的程式設計,需要啥功能就直接寫啥,但是我們在編寫程式的過程中會發現如果多個函式有共同的引數或資料時,我們也必須多次重複去寫,此時如果用面向物件的程式設計方式就會好很多,這也是面向物件的適用場景。
面向物件三大特性:
一、封裝(顧名思義就是將內容封裝到某個地方,以後再去呼叫被封裝在某處的內容,具體看下面的程式碼)
#!/usr/bin/env python# -*- coding:utf-8 -*- # Author: Xiaobai Lei class Person: def __init__(self, name, age): self.name = name self.age = age def get_msg(self): print(self.name) print(self.age) p1 = Person('xiaobai', 18) p1.get_msg() # Python預設會將p1傳給self引數,即:p1.get_msg(p1),所以,此時方法內部的 self = p1p2 = Person('xiaoming', 88) p2.get_msg() # 此處一樣將p2傳給self引數 # 對於面向物件的封裝來說,其實就是使用構造方法將內容封裝到物件中,然後通過物件直接或者self間接獲取被封裝的內容。
二、繼承(通俗來說就是繼承父類的所有東西,與現實一致)
# 2、繼承 class Person: def __init__(self, name, age): self.name = name self.age = age def eat(self):print("%s在吃飯" %self.name) # 在類後面括號中寫入另外一個類名,表示當前類繼承另外一個類 class Teacher(Person): def teacher(self): print("%s在教書" %self.name) t1 = Teacher("小白", 18) t1.eat() t1.teacher() # 對於面向物件的繼承來說,其實就是將多個類共有的方法提取到父類中,子類僅需繼承父類而不必一一實現每個方法。
除了上面的單繼承以外還有多繼承,ython的類如果繼承了多個類,那麼其尋找方法的方式有兩種,分別是:深度優先和廣度優先,詳情往下看:
- 當類是經典類時,多繼承情況下,會按照深度優先方式查詢
- 當類是新式類時,多繼承情況下,會按照廣度優先方式查詢
經典類和新式類,從字面上可以看出一個老一個新,新的必然包含了跟多的功能,也是之後推薦的寫法,從寫法上區分的話,如果 當前類或者父類繼承了object類,那麼該類便是新式類,否則便是經典類。
經典類多繼承如下:
class D: def bar(self): print('D.bar') class C(D): def bar(self): print('C.bar') class B(D): def bar(self): print('B.bar') class A(B, C): def bar(self): print('A.bar') a = A() # 執行bar方法時 # 首先去A類中查詢,如果A類中沒有,則繼續去B類中找,如果B類中麼有,則繼續去D類中找,如果D類中麼有,則繼續去C類中找,如果還是未找到,則報錯 # 所以,查詢順序:A --> B --> D --> C # 在上述查詢bar方法的過程中,一旦找到,則尋找過程立即中斷,便不會再繼續找了 a.bar() # 對於同一個根需要注意 class D: def bar1(self): print('D.bar') class C(D): def bar1(self): print('C.bar') class B(D): def bar(self): print('B.bar') class A(B, C): def bar(self): print('A.bar') a = A() # 執行bar1方法時 # 首先去A類中查詢,如果A類中沒有,則繼續去B類中找,如果B類中沒有,按理說應該去D類中找了,但是D類是B和C的同一個根類,所以先不找,先找C,C找不到才會最後找D這個共同的根類 # 所以,查詢順序:A --> B --> C --> D # 在上述查詢bar1方法的過程中,一旦找到,則尋找過程立即中斷,便不會再繼續找了 a.bar1()
新式類多繼承如下:
class D(object): def bar(self): print('D.bar') class C(D): def bar(self): print('C.bar') class B(D): def bar(self): print('B.bar') class A(B, C): def bar(self): print('A.bar') a = A() # 執行bar方法時 # 首先去A類中查詢,如果A類中沒有,則繼續去B類中找,如果B類中麼有,則繼續去C類中找,如果C類中麼有,則繼續去D類中找,如果還是未找到,則報錯 # 所以,查詢順序:A --> B --> C --> D # 在上述查詢bar方法的過程中,一旦找到,則尋找過程立即中斷,便不會再繼續找了 a.bar()
經典類:首先去A類中查詢,如果A類中沒有,則繼續去B類中找,如果B類中麼有,則繼續去D類中找,如果D類中麼有,則繼續去C類中找,如果還是未找到,則報錯
新式類:首先去A類中查詢,如果A類中沒有,則繼續去B類中找,如果B類中麼有,則繼續去C類中找,如果C類中麼有,則繼續去D類中找,如果還是未找到,則報錯
注意:在上述查詢過程中,一旦找到,則尋找過程立即中斷,便不會再繼續找了
三、多型(Pyhon不支援Java和C#這一類強型別語言中多型的寫法,但是原生多型,其Python崇尚“鴨子型別”。)
# Python的鴨子型別 class Duck(object): #Duck型別 def walk(self): print('i am a duck,and i can walk') def swim(self): print('i am a duck,and i can swim') class Cat(object): #Cat型別 def walk(self): print('i am a cat,and i can walk') def swim(self): print('i am a cat,and i can swim') # 實現一個動物walk和swim的功能函式 def walk_swim(animal): animal.walk() animal.swim() d = Duck() c = Cat() walk_swim(d) walk_swim(c)
以上就是本節對於面向物件初級知識的介紹,總結如下:
- 面向物件是一種程式設計方式,此程式設計方式的實現是基於對 類 和 物件 的使用
- 類 是一個模板,模板中包裝了多個“函式”供使用
- 物件,根據模板建立的例項(即:物件),例項用於呼叫被包裝在類中的函式
- 面向物件三大特性:封裝、繼承和多型