【Python】Python的類和對象(長文系列第⑤篇)
系列最后一篇來說說Python中的類與對象,Python這門語言是無處不對象,如果你曾淺要了解過Python,你應(yīng)該聽過Python是一種面向?qū)ο缶幊痰恼Z言,所以你經(jīng)??赡軙吹矫嫦颉皩ο蟆本幊踢@類段子,而面向?qū)ο缶幊痰恼Z言都會有三大特征:封裝、繼承、多態(tài)。
我們平時接觸到的很多函數(shù)、方法的操作都具有這些性質(zhì),我們只是會用,但還沒有去深入了解它的本質(zhì),下面就介紹一下關(guān)于類和對象的相關(guān)知識。
封裝
封裝這個概念應(yīng)該并不陌生,比如我們把一些數(shù)據(jù)封裝成一個列表,這就屬于數(shù)據(jù)封裝,我們也可以將一些代碼語句封裝成一個函數(shù)方便調(diào)用,這就是代碼的封裝,我們也可以將數(shù)據(jù)和代碼封裝在一起。用術(shù)語表示的話,就是可以將屬性和方法進(jìn)行封裝,從而得到對象。
首先我們可以定義一個類,這個類中有屬性和方法,但有的伙伴會比較好奇,屬性和方法不是會封裝成對象嘛,為什么又變成類了?舉個例子,類就好比是一個毛坯房,而對象是在毛坯房的基礎(chǔ)上改造成的精裝房。
class?XiaoMing:
????#屬性
????height?=?180
????weight?=?65
????sex?=?'男'
????#方法
????def?run(self):
????????print('小明在跑步')
????def?sleep(self):
????????print('小明在睡覺')
在類定義完成時就創(chuàng)建了一個類對象,它是對類定義創(chuàng)建的命名空間進(jìn)行了一個包裝。類對象支持兩種操作:屬性引用和實例化。
屬性引用的語法就是一般的標(biāo)準(zhǔn)語法:obj.name。比如XiaoMing.height和XiaoMing.run就是屬性引用,前者會返回一條數(shù)據(jù),而后者會返回一個方法對象。
In[1]:print(XiaoMing.height)
Out[1]:180
In[2]:print(XiaoMing.run)
Out[2]:0x0000021C6239D0D0>
這里也支持對類屬性進(jìn)行賦值操作,比如為類中的weight屬性賦予一個新值。
In[3]:print(XiaoMing.weight)
Out[3]:65
In[4]:XiaoMing.weight?=?100
In[5]:print(XiaoMing.weight)
Out[5]:100
而類的實例化可以將類對象看作成一個無參函數(shù)的賦值給一個局部變量,如下:
In[6]:ming?=?XiaoMing()
ming就是由類對象實例化后創(chuàng)建的一個實例對象,通過實例對象也可以調(diào)用類中的屬性和方法。
In[7]:ming.run()
Out[7]:小明在跑步
In[8]:print(xiaoming.height)
Out[8]:180
#通過向類對象調(diào)用方法返回的方法對象中傳入實例對象也可以達(dá)到同樣效果
In[11]:XiaoMing.run(ming)
Out[11]:小明在跑步
魔法方法__init__
類在實例化過程中并不都是像上面例子一樣簡單的,一般類都會傾向?qū)嵗龑ο髣?chuàng)建為有初始狀態(tài)的,所以在類中可能會定義一個__init__的魔法方法,這個方法就可以幫助接收、傳入?yún)?shù)。
而一個類如果定義了__init__方法,那么在類對象實例化的過程中就會自動為新創(chuàng)建的實例化對象調(diào)用__init__方法,請看下面這個例子。
class?Coordinates:
????def?__init__(self,x,y):
????????self.x?=?x
????????self.y?=?y
????def?print_coor(self):
????????print('當(dāng)前坐標(biāo)為(%s,%s)'%(self.x,self.y))
可以看到在__init__()中傳入了參數(shù)x和y,然后在print_coor中需要接收參數(shù)x和y,接下來通過實例化這個類對象,驗證一下參數(shù)是否能通過__init__()傳遞到類的實例化操作中。
In[9]:coor?=?Coordinates(5,3)
In[10]:coor.print_coor()
Out[10]:當(dāng)前坐標(biāo)為(5,3)
繼承
所謂繼承就是一個新類在另一個類的基礎(chǔ)上構(gòu)建而成,這個新類被稱作子類或者派生類,而另一個類被稱作父類、基類或者超類,而子類會繼承父類中已有的一些屬性和方法。
class?Mylist(list):
????pass
list_?=?Mylist()
list_.append(1)
print(list_)
'''
[1]
'''
class?Parent:
????def?par(self):
????????print('父類方法')
class?Child(Parent):
????pass
child?=?Child()
child.par()
'''
父類方法
'''
覆蓋
class?Parent:
????def?par(self):
????????print('父類方法')
class?Child(Parent):
????def?par(self):
????????print('子類方法')
child?=?Child()
child.par()
'''
子類方法
'''
多態(tài)
class?XiaoMing:
????def?introduce(self):
????????print("我是小明")
class?XiaoHong:
????def?introduce(self):
????????print("我是小紅")
In[12]:ming?=?XiaoMing()
In[13]:hong?=?XiaoHong()
In[14]:ming.introduce()
Out[14]:我是小明
In[15]:hong.introduce()
Out[15]:我是小紅
常用BIF
1、isssubclass(class,classinfo)
class?Parent:
????pass
class?Child(Parent):
????pass
print(issubclass(Child,Parent))
'''
True
'''
1.第二個參數(shù)不僅可以傳入類,也可以傳入由類組成的元組。 2.一個類被判定為自身的子類,也就是說這兩個參數(shù)傳入同一個類時,也會返回True。
print(issubclass(Parent,Parent))
'''
True
'''
2、isinstance(object,classinfo)
class?Parent:
????pass
class?Child:
????pass
p?=?Parent()
c?=?Child()
print(isinstance(p,Parent,Child))
#True
print(isinstance(c,Parent))
#False
1.第二個參數(shù)不僅可以傳入類,也可以傳入由類組成的元組。 2.如果第一個參數(shù)傳入的不是一個對象,則總是返回False。
3、hasattr(object,name)
class?Parent:
????height?=?100
p?=?Parent()
print(hasattr(p,'height'))
'''
True
'''
往期精彩回顧
