在本文中,您將學(xué)習(xí)Python的核心功能,Python對(duì)象和類。 您將學(xué)習(xí)什么是類,如何創(chuàng)建它并在程序中使用它。
Python是一種面向?qū)ο蟮木幊陶Z(yǔ)言。與面向過(guò)程的程序設(shè)計(jì)主要側(cè)重于函數(shù),面向?qū)ο蟮某绦蛟O(shè)計(jì)著重于對(duì)象。
對(duì)象只是數(shù)據(jù)(變量)和作用于這些數(shù)據(jù)的方法(函數(shù))的集合。并且,類是對(duì)象的藍(lán)圖。
我們可以將類視為房子的草圖(原型)。它包含有關(guān)地板,門,窗戶等的所有詳細(xì)信息?;谶@些描述,我們建造了房屋。房子是對(duì)象。
由于可以通過(guò)描述來(lái)制作許多房屋,因此我們可以根據(jù)類創(chuàng)建許多對(duì)象。對(duì)象也稱為類的示例,創(chuàng)建該對(duì)象的過(guò)程稱為示例化。
就像函數(shù)定義以關(guān)鍵字def開(kāi)頭一樣,在Python中,我們使用關(guān)鍵字class定義了一個(gè)類。
第一個(gè)字符串稱為docstring,并具有有關(guān)該類的簡(jiǎn)短說(shuō)明。盡管不是強(qiáng)制性的,但是建議這樣做。
這是一個(gè)簡(jiǎn)單的類定義。
class MyNewClass: '''這是一個(gè)文檔字符串。我已經(jīng)創(chuàng)建了一個(gè)新類''' pass
一個(gè)類創(chuàng)建一個(gè)新的本地命名空間,并在其中定義其所有屬性。屬性可以是數(shù)據(jù)或函數(shù)。
其中還有一些特殊屬性,它們以雙下劃線(__)開(kāi)頭。例如,__doc__給我們?cè)擃惖奈臋n字符串。
一旦定義了一個(gè)類,就會(huì)創(chuàng)建一個(gè)具有相同名稱的新類對(duì)象。這個(gè)類對(duì)象使我們可以訪問(wèn)不同的屬性以及示例化該類的新對(duì)象。
class MyClass: "這是我的第二個(gè)類" a = 10 def func(self): print('Hello') # 輸出: 10 print(MyClass.a) # 輸出: <function MyClass.func at 0x0000000003079BF8> print(MyClass.func) # 輸出: '這是我的第二個(gè)類' print(MyClass.__doc__)
運(yùn)行該程序時(shí),輸出為:
10 <function 0x7feaa932eae8="" at="" myclass.func=""> 這是我的第二個(gè)類
我們看到了類對(duì)象可用于訪問(wèn)不同的屬性。
它也可以用于創(chuàng)建該類的新對(duì)象示例(示例化)。創(chuàng)建對(duì)象的過(guò)程類似于函數(shù)調(diào)用。
>>> ob = MyClass()
這將創(chuàng)建一個(gè)新的示例對(duì)象ob。我們可以使用對(duì)象名稱前綴來(lái)訪問(wèn)對(duì)象的屬性。
屬性可以是數(shù)據(jù)或方法。對(duì)象的方法是該類的相應(yīng)函數(shù)。任何作為類屬性的函數(shù)對(duì)象都為該類的對(duì)象定義了一種方法。
這意味著,由于MyClass.func是函數(shù)對(duì)象(類的屬性),因此ob.func將成為方法對(duì)象。
class MyClass: "這是我的第二個(gè)類" a = 10 def func(self): print('Hello') # 創(chuàng)建一個(gè)新的MyClass ob = MyClass() # 輸出: <function MyClass.func at 0x000000000335B0D0> print(MyClass.func) # 輸出: <bound method MyClass.func of <__main__.MyClass object at 0x000000000332DEF0>> print(ob.func) # Calling function func() # 輸出: Hello ob.func()
您可能已經(jīng)注意到了類內(nèi)部函數(shù)定義中的self參數(shù),但是,我們只是將該方法簡(jiǎn)稱為ob.func(),沒(méi)有任何參數(shù)。它仍然有效。
這是因?yàn)?,只要?duì)象調(diào)用其方法,該對(duì)象本身就會(huì)作為第一個(gè)參數(shù)傳遞。因此,ob.func()自動(dòng)轉(zhuǎn)成MyClass.func(ob)。
通常,調(diào)用帶有n個(gè)參數(shù)列表的方法等效于調(diào)用帶有參數(shù)列表的函數(shù),該參數(shù)列表是通過(guò)在第一個(gè)參數(shù)之前插入方法的對(duì)象而創(chuàng)建的。
由于這些原因,類中函數(shù)的第一個(gè)參數(shù)必須是對(duì)象本身。這通常稱為self??梢允褂闷渌Q,但我們強(qiáng)烈建議您遵循約定。
現(xiàn)在,您必須熟悉類對(duì)象,示例對(duì)象,函數(shù)對(duì)象,方法對(duì)象及其區(qū)別。
以雙下劃線(__)開(kāi)頭的類函數(shù)被稱為特殊函數(shù),因?yàn)樗鼈兙哂刑厥夂x。
__init__()函數(shù)特別有用。每當(dāng)示例化該類的新對(duì)象時(shí),都會(huì)調(diào)用此特殊函數(shù)。
這種類型的函數(shù)在面向?qū)ο缶幊?OOP)中也稱為構(gòu)造函數(shù)。我們通常使用它來(lái)初始化所有變量。
class ComplexNumber: def __init__(self,r = 0,i = 0): self.real = r self.imag = i def getData(self): print("{0}+{1}j".format(self.real,self.imag)) # 創(chuàng)建一個(gè)新的ComplexNumber對(duì)象 c1 = ComplexNumber(2,3) # 調(diào)用getData()函數(shù) # 輸出: 2+3j c1.getData() # 創(chuàng)建另一個(gè)ComplexNumber對(duì)象 # 并創(chuàng)建一個(gè)新的屬性“attr” c2 = ComplexNumber(5) c2.attr = 10 # 輸出: (5, 0, 10) print((c2.real, c2.imag, c2.attr)) # 但c1對(duì)象沒(méi)有屬性" attr " # AttributeError: 'ComplexNumber'對(duì)象沒(méi)有屬性'attr' c1.attr
在上面的示例中,我們定義了一個(gè)新類來(lái)表示復(fù)數(shù)。它具有兩個(gè)函數(shù),以 __init__() 初始化變量(默認(rèn)為零),getData()用來(lái)正確顯示數(shù)字。
在上述步驟中需要注意的一件有趣的事情是,可以動(dòng)態(tài)地創(chuàng)建對(duì)象的屬性。我們?yōu)閷?duì)象c2創(chuàng)建了一個(gè)新的屬性attr,并讀取它。但這并沒(méi)有為對(duì)象c1創(chuàng)建該屬性。
可以使用del語(yǔ)句隨時(shí)刪除對(duì)象的任何屬性。在Python Shell上嘗試以下操作以查看輸出。
>>> c1 = ComplexNumber(2,3) >>> del c1.imag >>> c1.getData() Traceback (most recent call last): ... AttributeError: 'ComplexNumber' object has no attribute 'imag' >>> del ComplexNumber.getData >>> c1.getData() Traceback (most recent call last): ... AttributeError: 'ComplexNumber' object has no attribute 'getData'
我們甚至可以使用del語(yǔ)句刪除對(duì)象本身。
>>> c1 = ComplexNumber(1,3) >>> del c1 >>> c1 Traceback (most recent call last): ... NameError: name 'c1' is not defined
實(shí)際上,它比這更復(fù)雜。完成后,將在內(nèi)存中創(chuàng)建一個(gè)新的示例對(duì)象 c1 = ComplexNumber(1,3),名稱c1與 其綁定。
命令del c1,將刪除此綁定,并從相應(yīng)的名稱空間中刪除名稱c1。但是,該對(duì)象繼續(xù)存在于內(nèi)存中,如果沒(méi)有其他名稱綁定,則該對(duì)象以后會(huì)自動(dòng)銷毀。
在Python中這種對(duì)未引用對(duì)象的自動(dòng)銷毀也稱為垃圾回收。