Python物件導向(類和物件) - tw511教學網

文章推薦指數: 80 %
投票人數:10人

自從存在以來,Python一直是物件導向的語言。

因此,建立和使用類和物件是非常容易的。

本章將學習如何使用Python物件導向程式設計。

如果您以前沒有物件導向(OO)程式設. Python教學»Python物件導向(類和物件) 目錄 1.Python教學 2.Python快速入門 3.Python是什麼? 4.Python的歷史 5.Python功能特點 6.Python可以開發哪些程式? 7.Python安裝和環境組態 8.Python命令列引數 9.Python變數型別 10.Python基本運算子 11.Python決策 12.Python迴圈 13.Python數位 14.Python字串 15.Python列表 16.Python元組 17.Python字典 18.Python日期和時間 19.Python函式 20.Python模組 21.Python檔案讀寫 22.Python物件導向(類和物件) 23.Python建構函式 24.Python繼承 25.Python多重繼承 26.Python操作符過載 27.Python例外處理 28.Python正規表示式 29.Python+MySQL資料庫操作(PyMySQL) 30.Python網路程式設計(Sockets) 31.Python傳送郵件 32.Python多執行緒程式設計 33.PythonXML解析和處理 34.Python檔案物件方法 35.Pythonos模組方法 36.Python疊代器 37.Python生成器 38.Python閉包 39.Python修飾器 Python物件導向(類和物件) 自從存在以來,Python一直是物件導向的語言。

因此,建立和使用類和物件是非常容易的。

本章將學習如何使用Python物件導向程式設計。

如果您以前沒有物件導向(OO)程式設計的經驗,可能需要查閱介紹物件導向(OO)程式設計課程或至少學習一些有關教學,以便掌握基本概念。

下面是物件導向程式設計(OOP)的一個小介紹,以幫助您快速入門學習- OOP術語概述 類-用於定義表示使用者定義物件的一組屬性的原型。

屬性是通過點符號存取的資料成員(類變數和範例變數)和方法。

類變數-由類的所有範例共用的變數。

類變數在類中定義,但在類的任何方法之外。

類變數不像範例變數那樣頻繁使用。

資料成員-儲存與類及其物件相關聯的資料的類變數或範例變數。

函式過載-將多個行為分配給特定函式。

執行的操作因涉及的物件或引數的型別而異。

範例變數-在方法中定義並僅屬於類的當前範例的變數。

繼承-將類的特徵傳遞給從其派生的其他類。

範例-某個類的單個物件。

例如,物件obj屬於Circle類,它是Circle類的範例。

範例化-建立類的範例。

方法-在類定義中定義的一種特殊型別的函式。

物件-由其類定義的資料結構的唯一範例。

物件包括資料成員(類變數和範例變數)和方法。

運算子過載-將多個函式分配給特定的運算子。

1.建立類class語句建立一個新的類定義。

類的名稱緊跟在class關鍵字之後,在類的名稱之後緊跟冒號,如下- classClassName: 'Optionalclassdocumentationstring' class_suite 該類有一個文件字串,可以通過ClassName.__doc__存取。

class_suite由定義類成員,資料屬性和函式的所有元件語句組成。

範例 以下是一個簡單的Python類的例子- classEmployee: 'Commonbaseclassforallemployees' empCount=0 def__init__(self,name,salary): self.name=name self.salary=salary Employee.empCount+=1 defdisplayCount(self): print"TotalEmployee%d"%Employee.empCount defdisplayEmployee(self): print"Name:",self.name,",Salary:",self.salary 變數empCount是一個類變數,其值在此類中的所有範例之間共用。

這可以從類或類之外的Employee.empCount存取。

第一個方法__init__()是一種特殊的方法,當建立此類的新範例時,該方法稱為Python建構函式或初始化方法。

宣告其他類方法,如正常函式,但每個方法的第一個引數是self。

Python將self引數新增到列表中;呼叫方法時不需要包含它。

2.建立範例物件要建立類的範例,可以使用類名呼叫該類,並傳遞其__init__方法接受的任何引數。

##ThiswouldcreatefirstobjectofEmployeeclass emp1=Employee("Maxsu",2000) ##ThiswouldcreatesecondobjectofEmployeeclass emp2=Employee("Kobe",5000) 3.存取屬性可以使用帶有物件的點(.)運算子來存取物件的屬性。

類變數將使用類名存取如下- emp1.displayEmployee() emp2.displayEmployee() print("TotalEmployee%d"%Employee.empCount) 現在把所有的概念放在一起- #!/usr/bin/python3 classEmployee: 'Commonbaseclassforallemployees' empCount=0 def__init__(self,name,salary): self.name=name self.salary=salary Employee.empCount+=1 defdisplayCount(self): print("TotalEmployee%d"%Employee.empCount) defdisplayEmployee(self): print("Name:",self.name,",Salary:",self.salary) #ThiswouldcreatefirstobjectofEmployeeclass" emp1=Employee("Maxsu",2000) #ThiswouldcreatesecondobjectofEmployeeclass" emp2=Employee("Kobe",5000) emp1.displayEmployee() emp2.displayEmployee() print("TotalEmployee%d"%Employee.empCount) 當執行上述程式碼時,會產生以下結果- Name:Maxsu,Salary:2000 Name:Kobe,Salary:5000 TotalEmployee2 可以隨時新增,刪除或修改類和物件的屬性- emp1.salary=7000#Addan'salary'attribute. emp1.name='xyz'#Modify'age'attribute. delemp1.salary#Delete'age'attribute. 如果不是使用普通語句存取屬性,可以使用以下函式- getattr(obj,name[,default])-存取物件的屬性。

hasattr(obj,name)-檢查屬性是否存在。

setattr(obj,name,value)-設定一個屬性。

如果屬性不存在,那麼它將被建立。

delattr(obj,name)-刪除一個屬性。

下面是一此使用範例- hasattr(emp1,'salary')#Returnstrueif'salary'attributeexists getattr(emp1,'salary')#Returnsvalueof'salary'attribute setattr(emp1,'salary',7000)#Setattribute'salary'at7000 delattr(emp1,'salary')#Deleteattribute'salary' 3.內建類屬性每個Python類保持以下內建屬性,並且可以像任何其他屬性一樣使用點運算子存取它們- __dict__-包含該類的名稱空間的字典。

__doc__-類文件字串或無,如果未定義。

__name__-類名。

__module__-定義類的模組名稱。

此屬性在互動模式下的值為「main」。

__bases__-一個包含基礎類別的空元組,按照它們在基礎類別列表中出現的順序。

對於上述類,嘗試存取所有這些屬性- #!/usr/bin/python3 classEmployee: 'Commonbaseclassforallemployees' empCount=0 def__init__(self,name,salary): self.name=name self.salary=salary Employee.empCount+=1 defdisplayCount(self): print("TotalEmployee%d"%Employee.empCount) defdisplayEmployee(self): print("Name:",self.name,",Salary:",self.salary) emp1=Employee("Maxsu",2000) emp2=Employee("Bryant",5000) print("Employee.__doc__:",Employee.__doc__) print("Employee.__name__:",Employee.__name__) print("Employee.__module__:",Employee.__module__) print("Employee.__bases__:",Employee.__bases__) print("Employee.__dict__:",Employee.__dict__) 當執行上述程式碼時,會產生以下結果- Employee.__doc__:Commonbaseclassforallemployees Employee.__name__:Employee Employee.__module__:__main__ Employee.__bases__:(,) Employee.__dict__:{ 'displayCount':, '__module__':'__main__','__doc__':'Commonbaseclassforallemployees', 'empCount':2,'__init__': ,'displayEmployee': , '__weakref__': ,'__dict__': } 4.銷毀物件(垃圾收集)Python自動刪除不需要的物件(內建型別或類範例)以釋放記憶體空間。

Python定期回收不再使用的記憶體塊的過程稱為垃圾收集。

Python的垃圾收集器在程式執行期間執行,當物件的參照計數達到零時觸發。

物件的參照計數隨著指向它的別名數量而變化。

當物件的參照計數被分配一個新名稱或放置在容器(列表,元組或字典)中時,它的參照計數會增加。

當用del刪除物件的參照計數時,參照計數減少,其參照被重新分配,或者其參照超出範圍。

當物件的參照計數達到零時,Python會自動收集它。

a=40#Createobject<40> b=a#Increaseref.countof<40> c=[b]#Increaseref.countof<40> dela#Decreaseref.countof<40> b=100#Decreaseref.countof<40> c[0]=-1#Decreaseref.countof<40> 通常情況下,垃圾回收器會銷毀孤立的範例並回收其空間。

但是,類可以實現呼叫解構函式的特殊方法__del__(),該方法在範例即將被銷毀時被呼叫。

此方法可能用於清理範例使用的任何非記憶體資源。

範例 這個__del__()解構函式列印要被銷毀的範例的類名- #!/usr/bin/python3 classPoint: def__init__(self,x=0,y=0): self.x=x self.y=y def__del__(self): class_name=self.__class__.__name__ print(class_name,"destroyed") pt1=Point() pt2=pt1 pt3=pt1 print(id(pt1),id(pt2),id(pt3));#printstheidsoftheobejcts delpt1 delpt2 delpt3 當執行上述程式碼時,會產生以下結果- 308340132430834013243083401324 Pointdestroyed 注意-理想情況下,應該在單獨的檔案中定義類,然後使用import語句將其匯入主程式檔案。

在上面的例子中,假定Point類的定義包含在point.py中,並且其中沒有其他可執行程式碼。

#!/usr/bin/python3 importpoint p1=point.Point() 5.類繼承使用類繼承不用從頭開始構建程式碼,可以通過在新類名後面的括號中列出父類別來從一個預先存在的類派生它來建立一個類。

子類繼承其父類別的屬性,可以像子類中一樣定義和使用它們。

子類也可以從父類別代替代資料成員和方法。

語法 派生類被宣告為很像它們的父類別;然而,繼承的基礎類別的列表在類名之後給出- classSubClassName(ParentClass1[,ParentClass2,...]): 'Optionalclassdocumentationstring' class_suite 範例 #!/usr/bin/python3 classParent:#defineparentclass parentAttr=100 def__init__(self): print("Callingparentconstructor") defparentMethod(self): print('Callingparentmethod') defsetAttr(self,attr): Parent.parentAttr=attr defgetAttr(self): print("Parentattribute:",Parent.parentAttr) classChild(Parent):#definechildclass def__init__(self): print("Callingchildconstructor") defchildMethod(self): print('Callingchildmethod') c=Child()#instanceofchild c.childMethod()#childcallsitsmethod c.parentMethod()#callsparent'smethod c.setAttr(200)#againcallparent'smethod c.getAttr()#againcallparent'smethod 當執行上述程式碼時,會產生以下結果- Callingchildconstructor Callingchildmethod Callingparentmethod Parentattribute:200 以類似的方式,可以從多個父類別來構建一個新的類,如下所示: classA:#defineyourclassA ..... classB:#defineyourcalssB ..... classC(A,B):#subclassofAandB ..... 可以使用issubclass()或isinstance()函式來檢查兩個類和範例之間的關係。

issubclass(sub,sup)布林函式如果給定的子類sub確實是超類sup的子類返回True。

isinstance(obj,Class)布林函式如果obj是類Class的一個範例,或者是類的一個子類的範例則返回True。

過載方法可以隨時過載父類別的方法。

過載父方法的一個原因是:您可能希望在子類中使用特殊或不同的方法功能。

範例 #!/usr/bin/python3 classParent:#defineparentclass defmyMethod(self): print('Callingparentmethod') classChild(Parent):#definechildclass defmyMethod(self): print('Callingchildmethod') c=Child()#instanceofchild c.myMethod()#childcallsoverriddenmethod 當執行上述程式碼時,會產生以下結果- Callingchildmethod 基本過載方法下表列出了可以在自己的類中覆蓋的一些通用方法- 編號 方法 描述 呼叫範例 1 __init__(self[,args...]) 建構函式(帶任意可選引數) obj=className(args) 2 __del__(self) 解構函式,刪除一個物件 delobj 3 __repr__(self) 可評估求值的字串表示 repr(obj) 4 __str__(self) 可列印的字串表示 str(obj) 5 __cmp__(self,x) 物件比較 cmp(obj,x) 6.過載運算子假設已經建立了一個Vector類來表示二維向量。

當使用加號(+)運算子執行運算時,它們會發生什麼?很可能Python理解不了你想要做什麼。

但是,可以在類中定義__add__方法來執行向量加法,然後將按照期望行為那樣執行加法運算- 範例 #!/usr/bin/python3 classVector: def__init__(self,a,b): self.a=a self.b=b def__str__(self): return'Vector(%d,%d)'%(self.a,self.b) def__add__(self,other): returnVector(self.a+other.a,self.b+other.b) v1=Vector(2,10) v2=Vector(5,-2) print(v1+v2) 當執行上述程式碼時,會產生以下結果- Vector(7,8) 7.資料隱藏物件的屬性在類定義之外可能或不可見。

需要使用雙下劃線字首命名屬性,然後這些屬性將不會直接對外部可見。

範例 #!/usr/bin/python3 classJustCounter: __secretCount=0 defcount(self): self.__secretCount+=1 print(self.__secretCount) counter=JustCounter() counter.count() counter.count() print(counter.__secretCount) 當執行上述程式碼時,會產生以下結果- 1 2 Traceback(mostrecentcalllast): File"test.py",line12,in printcounter.__secretCount AttributeError:JustCounterinstancehasnoattribute'__secretCount' Python通過內部更改名稱來包含類名稱來保護這些成員。

可以存取object._className__attrName等屬性。

如果將最後一行替換為以下,那麼它適用於- ......................... print(counter._JustCounter__secretCount) 當執行上述程式碼時,會產生以下結果- 1 2 2 Python檔案讀寫 Python建構函式



請為這篇文章評分?