【python小課堂專欄】python小課堂19 - 面向物件篇(二)
python小課堂19 - 面向物件篇(二)
前言
哈嘍呀Everybody,又到了更新干貨的時間了,繼續python小課堂的迴歸之路,面向物件篇的第二章,面向物件的涉及的東西實在是太多了,所以打算拆開三次寫吧,後面還有一次面向物件篇,但是打算寫完這篇之後用面向物件的設計思想來一波實戰篇教學,依然是和安全相關的,敬請期待…
例項物件中的self
回顧下上一章中,學習了定義一個物件(類)的方法,並且這個類中有自己的類變數以及實力變數,還有自己對應的方法以及構造方法。在例項方法中有個特殊的關鍵詞需要預設傳入 – self 。來看下引用上節的例子。
class GirlFriend ():
# 交過的女朋友個數
total_nums = 0
# 初始化構造方法
def __init__(self,name,age):
self.name = name
self.age = age
# 行為,說出自己的特徵
def say_feature(self):
print(f'我的姓名:{self.name}')
print(f'我的年齡:{self.age}')
girlFriend = GirlFriend('人類女孩',18) # 例項化
girlFriend. say_feature()
實際上,self這個關鍵字並不一定非得叫self,如果學過java的同學一定知道this這個關鍵詞,特指在一個類中例項物件生成後的本身,而python中的self與其一致,我們可以將self修改成this來看下程式會不會正常執行。
可以看到上圖,改成this後依然成功執行,所以self只是python中的一個官方寫法,具體你要定義成什麼樣子的預設第一個引數,隨你喜好,但是推薦預設self就好啦。
例項物件中的變數機制(dict)
通過**dict** 可以檢視例項物件的屬性。什麼意思呢?來看下:
class GirlFriend():
# 交過的女朋友個數
total_nums = 0
# 初始化構造方法
def __init__(self, name, age):
self.name = name
self.age = age
# 行為,說出自己的特徵
def say_feature(self):
print(f'我的姓名:{self.name}')
print(f'我的年齡:{self.age}')
girlFriend = GirlFriend('人類女孩', 18) # 例項化
print(girlFriend.__dict__)
可以看到結果,將例項化後的物件中的變數成員以字典的形式打印出來,name和age是例項變數,而人類女孩和18便是我通過建立物件時傳入的引數。
例項方法訪問變數
例項方法:見名知意,即類中定義的方法,需要例項化物件後才能呼叫的方法稱之為例項方法。比如在上面的GirlFriend類中的say_feature(),就叫例項方法。那麼問題來了,例項方法可以直接訪問例項變數,這是大家都可以想到的,比如在say_feature()中通過self.name呼叫了例項變數name。那例項方法中如何訪問類的變數呢?在上面的程式碼中,類變數就是total_nums,也就是你迄今為止交過女朋友的總數量。
先來個錯誤的例子:
class GirlFriend():
# 交過的女朋友個數
total_nums = 0
# 初始化構造方法
def __init__(self, name, age):
self.name = name
self.age = age
print(f'訪問類變數total_nums:{total_nums}')
# 行為,說出自己的特徵
def say_feature(self):
print(f'我的姓名:{self.name}')
print(f'我的年齡:{self.age}')
girlFriend = GirlFriend('人類女孩', 18) # 例項化
print(girlFriend.__dict__)
看到控制檯報錯,輸出沒有定義total_nums,說明這種方式在例項方法中直接訪問類變數是錯誤的。
正確的例子1:
實際上在上一節的python小課堂的末尾處,提到過如何在類外訪問類變數,直接通過類.變數即可訪問,在例項物件內部也可以通過這種方式進行訪問。
正確的例子2:
# 通過 self.__class__ 呼叫類變數也可以進行呼叫
self.__class__.total_nums
類變數還有個特性,就是例項化物件將其共有,這種場景也許在以後的程式設計中會遇到,我這裡依然以女朋友舉例,每個例項變數是你每個不同女票的名字和年齡,而假設你每次交一個女票,這個交女朋友的總數total_nums就會增加1。
來看下程式碼示例:
class GirlFriend():
# 交過的女朋友個數
total_nums = 0
# 初始化構造方法
def __init__(self, name, age):
self.name = name
self.age = age
self.__class__.total_nums += 1
print(f'迄今為止交到的女朋友個數total_nums:{self.__class__.total_nums}')
# 行為,說出自己的特徵
def say_feature(self):
print(f'我的姓名:{self.name}')
print(f'我的年齡:{self.age}')
girlFriend = GirlFriend('人類女孩1', 18) # 例項化
girlFriend2 = GirlFriend('人類女孩2', 23) # 例項化
girlFriend3 = GirlFriend('人類女孩3', 20) # 例項化
看到結果,每次例項化一個女盆友,總數都會增加一次使用場景自行細細品味一番吧…
再多說一句,方法和變數之間的關係:變數其實就是我們日常所說的資料,而方法就是如何去處理資料,也就是將變數讀取後進行相關處理。這層處理關係就是方法和變數的關係!
類方法
在本章開篇處介紹了例項方法,那麼類方法則是不需要進行例項化物件,可以直接通過類.方法進行呼叫。來看下面的例子:
class GirlFriend():
# 交過的女朋友個數
total_nums = 0
# 初始化構造方法
def __init__(self, name, age):
self.name = name
self.age = age
# 行為,說出自己的特徵
def say_feature(self):
print(f'我的姓名:{self.name}')
print(f'我的年齡:{self.age}')
# 類方法
@classmethod
def make_girlfriend_count(cls):
cls.total_nums += 1
print(f'迄今為止交到的女朋友個數total_nums:{cls.total_nums}')
GirlFriend.make_girlfriend_count()
GirlFriend.make_girlfriend_count()
girlFriend = GirlFriend('人類女孩1', 18) # 例項化
girlFriend.make_girlfriend_count()
通過在方法上面加上 @classmethod,這樣來定義類方法,這個寫法可以先了解下,後序會講到python的裝飾器,就知道這種寫法的意義了。classmethod,中文翻譯就是類方法的意思,在方法的預設引數中,需要預設給出一個cls作為引數,這裡類似例項方法中的self欄位,他們都是形式上的預設引數,名字可以改變,不一定必須叫cls,python預設會給出cls,而cls是class的簡寫,也指代的是自己本身。
將交到女朋友的個數作為類方法來演示下最終的執行結果:
呼叫類方法時,只需要通過類名稱直接呼叫即可。當然python也支援先例項化在呼叫類方法,也不會報錯,可以看到上圖中最後一次 呼叫,但是絕不推薦這樣用,因為沒有意義!
靜態方法
靜態方法:定義時,不需要像類方法和例項方法預設傳入引數,在方法上面宣告一個叫@staticmethod的裝飾器,staticmethod,中文翻譯靜態方法。來看下寫法:
class GirlFriend():
# 交過的女朋友個數
total_nums = 0
# 初始化構造方法
def __init__(self, name, age):
self.name = name
self.age = age
# 行為,說出自己的特徵
def say_feature(self):
print(f'我的姓名:{self.name}')
print(f'我的年齡:{self.age}')
# 類方法
@classmethod
def make_girlfriend_count(cls):
cls.total_nums += 1
print(f'迄今為止交到的女朋友個數total_nums:{cls.total_nums}')
@staticmethod
def study_language(language,score):
print(f'我在學習{language},熟練分數:{score}')
GirlFriend.study_language('中文',90)
**注:**在靜態方法和類方法中,是無法直接用self.xxx引用例項變數的。可自行嘗試!
類方法和靜態方法的區別:在呼叫時,都可以通過類名直接進行呼叫。但是一般不推薦使用靜態方法,因為類方法同樣可以實現,並且可以通過預設引數cls直接引用類中的類變數使用。
總結
以上就是python面向物件的第二部分,後面我會畫一個思維導圖來整理下學到的相關知識,其實圖一畫出來,邏輯就非常清晰了。回顧下本章內容,介紹了self的應用,類方法的應用,例項方法的應用以及相互之間訪問的關係。文章略長,還望耐心觀看…切忌浮躁(也是說給自己的!)
至此完!
有想學python的同學,歡迎關注公號: