Python基礎之物件導向
引言,學習物件導向之前先討論一下程式設計思想 目前我們學了兩種程式設計思想。一是程式導向程式設計即流程,程式導向就是按照固定的解決流程解決問題,比如編寫註冊功能、登入功能、轉賬功能等,需要列舉出每一步的流程,並且隨著步驟的深入問題的解決思路越來越簡單,然後指定出該問題的解決方案,用函式關鍵字def來完成程式導向的程式設計。二是物件導向程式設計,有點類似於造物主的感覺 只需要造出一個個物件至於該物件將來會如何發展跟程式設計師沒有關係也無法控制,比如遊戲人物。用關鍵字class來定義出類來完成物件導向的程式設計。這兩種程式設計思想沒有優劣之分需要結合實際需求而定、實際上這兩種程式設計思想是彼此交融的只是佔比不同。如果需求是註冊登入 人臉識別那肯定使用用程式導向更合適。如果需求是遊戲人物肯定是物件導向更合適。物件導向並不是一門新的技術為了好區分定義出來了獨有的語法格式。那麼本篇文章接下來詳細的研究一下程式設計思想之一物件導向。
一、物件導向之類與物件
- 物件:資料與功能的結合體 是物件導向的核心 必須先定義出類才能用物件
- 類:多個物件相同資料和功能的結合體 主要是為了節省程式碼
1.類與物件的建立以及呼叫
class 類名:
'''程式碼註釋'''
物件公共的資料
物件公共的功能
"""
class 是定義類的官關鍵字
類名的命名跟變數名幾乎一直 但是要首字母大寫
資料是變數名與資料值得繫結
功能是方法其實就是函式
"""
類在定義階段就會執行類體程式碼 但是屬於類的區域性名稱空間 外界無法直接呼叫
類和物件訪問資料或者功能 可以統一採用句點符
類名加括號就會產生物件 並且每執行一次都會產生一個全新的物件
2.物件獨有的資料和功能
'''物件獨有資料'''
1.直接利用物件點名字的方式
obj1 = Student()
obj1.__dict__['name'] = 'almira'
obj1.age = 18
obj2 = Student()
obj2.__dict__['name'] = 'Alina'
obj2.age = 29
2.將新增物件獨有資料的程式碼封裝成函式
def init(obj,name,age):
obj.name = name # obj.__dict__['name'] = name
obj.age = age # obj.__dict__['age'] = age
3.將上述方法繫結給特定類的物件
class Student:
def init(obj,name,age):
obj.name = name # obj.__dict__['name'] = name
obj.age = age # obj.__dict__['age'] = age
4.自動觸發的方法
class Student:
def __init__(self,name,age):
self.name = name # obj.__dict__['name'] = name
self.age = age # obj.__dict__['age'] = age
5.類中如果有雙下init方法 意味著類加括號需要傳引數
obj = Student('almira', 18)
'''物件獨有的功能'''
1.也是直接在全域性定義函式 然後給物件
def func():pass
obj = Student()
obj.func = func
2.物件導向的思想 放到類中
3.物件的繫結方法
類中定義的方法既可以說是物件公共的方法 也可以是物件獨有的方法
哪個物件來呼叫 誰就是主人公
二、動靜態方法 在類體中定義函式的三種方式
1.類中直接定義函式 預設繫結給物件 類呼叫有幾個引數傳幾個闡述 物件呼叫第一個引數就是物件自身
class Student:
shcool_name = '天津財經大學'
def func1(self):
print('天才學子')
obj = Student()
# 1.繫結給物件的方法
obj.func1()
Student.func1(123)
2.被@classmethod修飾的函式 預設繫結給類 類呼叫第一個引數就是類自身 物件也可以呼叫並且會自動將產生該物件的類當做第一個引數傳入
class Student:
school_name = '天津財經大學'
@classmethod
def func2(cls):
print('是不是蒙了呢', cls)
obj = Student()
# 2.繫結給類的方法
Student.func2() # fun2(Student)
obj.func2() # func2(Student)
3.普普通通的函式 無論是類還是物件呼叫 都必須自己手動傳參
class Student:
school_name = '天津財經大學'
@staticmethod
def func3(a):
print('哈哈哈,我很煩',a)
obj = Student()
# 1.靜態方法
Student.func3(123)
obj.func3(321)
三、物件導向三大特徵之繼承
1.繼承的含義
在程式設計世界中繼承表示類與類之間資源的從屬關係 比如 類A繼承類B
2.繼承的目的
在程式設計世界中類A繼承類B就擁有了類B中所有的資料和方法使用權
3.繼承得本質
繼承的本質就是對某一批類的抽象,從而實現對現實世界更好的建模
4.繼承的實操
class Son(Father):
pass
'''括號裡面可以寫其他類名Son就繼承了Father'''
# 繼承其他類的類 Son 稱為子類派生類
class Son(F1, F2, F3):
pass
'''可以多繼承 在括號內的類名用逗號隔開即可'''
# 被繼承的類 Father F1, F2, F3 稱為父類、基類、超類
5.名字的查詢順序
- 不繼承:物件自身>>>產生物件的類
- 單繼承:物件自身>>>產生物件的類>>>類的父類們
- 多繼承:物件自身>>>產生物件的類>>>類的父類們
四、物件導向三大特徵之封裝
封裝:就是將資料和功能'封裝'起來
隱藏:將資料和功能隱藏起來不讓使用者直接呼叫 而是開發一些介面間接呼叫從而可以在介面內新增額外的操作
偽裝:將類裡面的方法偽裝成類裡面的資料
class C1:
__name = 'almira'
def __func(self):pass
'''也有可能會出現單個下劃線開頭的變數名也表示隱藏的意思或者沒有'''
class C2:
@property
def BMI(self):pass
五、物件導向三大特徵之多型
多型其實就是一種事物的多種形態 物件導向中的多型的意思是 一種事物可以有多種形態但是針對相同的功能應該定義相同的用法 這樣無論拿到的是那個具體的事物 都可以透過相同的方法呼叫功能
'''多個類如果有相似之處 那麼裡面針對相似的功能應該起相同的名字'''
class Memory:
def read(self):pass
class Disk:
def read(self):pass
'''鴨子型別實際案例'''
class QQ:
def send(self):pass
class Wechat:pass
def send(self):pass
class Email:pass
def send(self):pass
class Msg:pass
def send(self):pass
六、物件導向之反射
反射是指利用字串操作物件的資料或方法,從另一個角度分析的話反射能夠將物件導向的程式碼與用互動起來
hasattr() 判斷物件是否含有某個字串對應的屬性名或方法名
getattr() 根據字串獲取物件對應的屬性名或方法名
setattr() 根據字串物件設定或修改資料
delattr() 根據字串刪除物件裡面的名字
七、物件導向的魔法方法
魔法方法:類中定義的雙下方法 不需要人為呼叫 在特定的條件下會自動觸發執行 比如雙下init方法建立空物件之後自動觸發給物件新增獨有的資料如下列舉出來了一些魔法方法名稱個、和它的功能解釋
__init__ 物件新增獨有的資料的時候自動觸發
__str__ 物件被執行列印操作的時候自動觸發
__call__ 物件加括號呼叫的時候自動觸發
__getattr__ 物件點不存在的名字的時候自動觸發
__getatribute__ 物件點名字就會自動觸發
__setattr__ 給物件新增或者修改資料的時候自動觸發
__enter__ 當物件被當做with上下文管理操作的開始自動觸發
__exit__ 當with上下文管理語法執行完畢之後自動觸發
__new__ 可以產生空物件
__dict__ 以字典方式列印所有屬性
八、建立類的兩種方式
# 方式1:使用關鍵字class
class Student:
school_name = '天津財經大學'
def func1(self):pass
print(Student)
print(Student.__dict__)
# 方式2:使用元類type
格式:type(類名,類的父類,類的名稱空間)
cls = type('Student', (object,), {'name': 'almira'})
print(cls)
print(cls.__dict__)