日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > python >内容正文

python

python_面向对象

發布時間:2025/4/16 python 39 豆豆
生活随笔 收集整理的這篇文章主要介紹了 python_面向对象 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

面向對象編程
?? ?object(對象)
?? ?什么是對象
?? ??? ?對象是指現實中的物體或實物
?? ?什么是面向對象
?? ??? ?把一切看成對象(實例),讓對象和對象之間建立關聯關系
?? ?對象都有什么特征
?? ??? ?對象有很多屬性(名詞),用變量記錄屬性
?? ??? ??? ?姓名,年齡,性別等
?? ??? ?對象有很多行為(動作,動詞),用函數(方法)表示行為
?? ??? ??? ?學習,吃飯,睡覺,踢球,工作
?? ?什么是類class:
?? ??? ?擁有相同屬性和行為的對象分為一組,即為一個類
?? ??? ?類是用來描述對象的工具,用類可以創建同類對象
?? ?類的創建語句:
?? ??? ?語法:class 類名(繼承列表):
?? ??? ??? ??? ?'''類的文檔字符串'''
?? ??? ??? ??? ?實例方法定義(類內的函數稱為方法method)
?? ??? ??? ??? ?類變量定義
?? ??? ??? ??? ?類方法定義
?? ??? ??? ??? ?靜態方法定義
?? ??? ?作用:
?? ??? ??? ?1、創建一個類
?? ??? ??? ?2、用于描述此類對象的行為和屬性
?? ??? ??? ?3、類用于創建此類的一個或多個對象(實例)

class Dog:#定義一個類,類名為Dogpass dog1 = Dog()#創建Dog類的一個對象 print(id(dog1))#140399880349568 dog2 = Dog()#創建Dog類的另一個對象 print(id(dog2))#140399880349848 #類似于如下語句: int1 = int() int2 = int () View Code

??? 類 和 對象
?? ??? ?類?? |?? ?? 對象????? 實例
?? ?? class? |? object?? instance
?? ?構造函數
?? ??? ?表達式:類名([創建傳參列表])
?? ??? ?作用:創建這個類的實例對象,并返回此實例對象的引用關系
?? ?實例(對象)說明
?? ??? ?實例有自己的作用域和名字空間,可以為該實例添加實例變量(屬性)
?? ??? ?實例可以調用類方法和實例方法
?? ??? ?實例可以訪問類變量和實例變量
?? ?實例方法:
?? ??? ?語法:calss 類名(繼承列表):
?? ??? ??? ??? ?def 實例方法名(self,參數1,參數2...):
?? ??? ??? ??? ??? ?'''實例方法的的文檔字符串'''
?? ??? ??? ??? ??? ?語句塊
?? ??? ?作用:用于描述一個對象的行為,讓此類型的全部對象都擁有相同的行為
?? ??? ?說明:
?? ??? ??? ?1、實例方法實質是函數,是定義在類內的函數
?? ??? ??? ?2、實例方法至少有一個形參,第一個形參代表調用這個方法的實例,一般命名為”self“
?? ??? ?實例方法的調用語法:
?? ??? ??? ?1、實例.實例方法名(調用傳參)
?? ??? ??? ?2、類名.實例方法名(實例,調用傳參)

#此實例示意如何用實例方法(method)來描述Dog類的行為 class Dog():def eat(self,food):'''此方法用來描述小狗吃東西的行為'''print("小狗正常吃:",food)def sleep(self,hour):print("小狗睡了",hour,'小時') dog1 = Dog()#創建一個Dog的類的實例 dog1.eat("狗糧") dog1.sleep(1) Dog.eat(dog1,"狗糧")#第二種方法調用實例方法 #對象不能調用類內沒有的方法 View Code

??? 屬性 attribute(也叫實例變量)
?? ??? ?每個實例都可以有自己的變量,此變量稱為實例變量(也叫屬性)
?? ??? ?屬性的使用語法:實例名.屬性名
?? ??? ?賦值規則:
?? ??? ??? ?1、首次為屬性賦值,則創建此屬性
?? ??? ??? ?2、再次為屬性賦值,則必改變屬性的綁定關系
?? ??? ?作用:用來記錄對象自身的數據

class Dog:pass #創建第一個對象 dog1 = Dog() dog1.kinds = '京巴' #添加屬性kinds dog1.color = '白色' #添加屬性color dog1.color = '京巴' #改變屬性的綁定關系 View Code

??? 實例方法和實例變量(屬性)結合使用

class Dog:def eat(self,food):print("%s的%s正在吃%s"%(self.color,self.kinds,food)) dog1 = Dog() dog1.kinds = '京巴' #添加屬性kinds dog1.color = '白色' #添加屬性color dog1.eat("狗糧")#該語句不能放在kinds和color屬性被添加之前 dog2 = Dog() dog2.kinds = '哈士奇' #添加屬性kinds dog2.color = '黑色' #添加屬性color dog2.eat("包子") View Code

??? 刪除屬性
?? ??? ?用del語句可以刪除一個對象的實例變量
?? ??? ?語法:
?? ??? ??? ?del 對象.實例變量名
?? ??? ?示例:
?? ??? ??? ?class Cat:
?? ??? ??? ??? ?pass
?? ??? ??? ?c1 = Cat()?? ??? ?#創建實例對象
?? ??? ??? ?c1.color = "白色"#添加屬性
?? ??? ??? ?del c1.color? ??? ?#刪除屬性
?? ??? ??? ?print(c1.color)#屬性錯誤

?? ?初始化方法:
?? ??? ?作用:對新創建的對象添加實例變量(屬性)或相應的資源
?? ??? ?語法:
?? ??? ??? ?class 類名(繼承列表):
?? ??? ??? ??? ?def __init__(self[,形參列表]):
?? ??? ??? ??? ??? ?語句塊
?? ??? ?說明:
?? ??? ??? ?1、初始化方法名必須為__init__不可改變
?? ??? ??? ?2、初始化方法會在構造函數創建實例后自動調用,且將實例自身通過第一個參數self傳入__init__方法
?? ??? ??? ?3、構造函數的實參將通過__init__方法的形參傳入__init__方法中
?? ??? ??? ?4、初始化方法內部如果需要返回,則只能返回None

class Car():def __init__(self,c,b,m):#此方法只能怪返回Noneprint("__init__方法被調用")self.color = cself.brand = bself.model = m#return 1 #TypeError: __init__() should return None, not 'int' car = Car("紅色","奧迪","A4")#Car()構造函數首先創建一個空的(沒有屬性的對象),然后把這個對象傳遞給__init__方法 View Code

? 析構方法:
?? ??? ?語法:class 類名(繼承列表):
?? ??? ??? ?def __del__(self):
?? ??? ??? ??? ?語句塊
?? ??? ?說明:析構方法在對象銷毀時被自動調用
?? ??? ?作用:清理此對象所占用的資源
?? ??? ?python不建議在析構方法中做任何事情,因為對象銷毀的時間難以確定
?? ?預置實例屬性:
?? ??? ?__dict__屬性:
?? ??? ??? ?此屬性綁定一個存儲此實例自身實例變量(屬性)的字典,也可以存儲類中的變量,文檔字符串,方法
?? ??? ?示例:
?? ??? ??? ?class Dog():
?? ??? ??? ??? ?pass
?? ??? ??? ?dog = Dog()
?? ??? ??? ?print(dog.__dict__)#{}
?? ??? ??? ?dog.kinds = "aa"
?? ??? ??? ?print(dog.__dict__)#{"kinds":"aa"}
?? ??? ??? ?dog.__dict__["color"]= "red"
?? ??? ?__class__屬性:
?? ??? ??? ?此屬性用來綁定創建此實例的類
?? ??? ??? ?作用:可以借助此屬性來訪問創建此實例的類
?? ??? ??? ?示例:
?? ??? ??? ??? ?class Dog()
?? ??? ??? ??? ??? ?pass
?? ??? ??? ??? ?dog1=Dog()
?? ??? ??? ??? ?dog2 = dog1.__class__()#等同于dog2 = Dog()
?? ? 面向對象的綜合示例
?? ? ?? ?有兩個人:
?? ? ?? ??? ?1、姓名:張三? 年齡:35
?? ? ?? ??? ?2、姓名:李四? 年齡:38
?? ? ?? ?行為:
?? ? ?? ??? ?1、交別人學東西teach
?? ? ?? ??? ?2、賺錢
?? ? ?? ??? ?3、借錢
?? ? ?? ?事情:
?? ? ?? ??? ?張三 教 李四 學 python
?? ? ?? ??? ?李四 教 張三 學 跳皮筋
?? ? ?? ??? ?張三 上班賺了 1000 元錢
?? ? ?? ??? ?李四 向 張三 借了 200 元錢

class Person():'''人類,用于描述人的行為和屬性'''def __init__(self,name,age):self.name = nameself.age = ageself.money = 0def teach(self,other,things):print(self.name,"",other.name,"",things)def make_money(self,money):self.money+=moneyprint(self.name,"上班賺了",money,"元錢")def borrow_money(self,other,money):if other.money > money:# print(self.name,"",other.name,"借了",money,"元錢")other.money -= moneyself.money += moneyprint(other.name,"沒有錢借給",self.name)def show_info(self):print(self.age,"歲的",self.name,"存有",self.money,"元錢") p1 = Person("張三",35) p2 = Person("李四",38) p1.teach(p2,"python") p2.teach(p1,"跳皮筋") p1.make_money(1000) p2.borrow_money(p1,200) p1.show_info() p2.show_info() # 張三 教 李四 學 python # 李四 教 張三 學 跳皮筋 # 張三 上班賺了 1000 元錢 # 李四 向 張三 借了 200 元錢 # 張三 沒有錢借給 李四 # 35 歲的 張三 存有 800 元錢 # 38 歲的 李四 存有 200 元錢 View Code

?? ? 用于判斷類的函數:
?? ? ?? ?isinstance(obj,class_or_tuple)返回一個對象obj是否為某個類class或某些類的實例,如果是返回True,否則返回False
?? ? ?? ?type(obj)?? ?返回對象的類型
?? ? 示例:
?? ? ?? ??? ?class Dog:
?? ? ?? ??? ??? ?pass
?? ? ?? ??? ?class Cat:
?? ? ?? ??? ??? ?pass
?? ? ?? ??? ?animal = Dog()
?? ? ?? ??? ?isinstance(animal,Dog) #True
?? ? ?? ??? ?isinstance(animal,Cat) #False
?? ? ?? ??? ?isinstance(animal,(Cat,int,list)) #False
?? ? ?? ??? ?isinstance(animal,(Cat,int,list,Dog)) #True

類變量 class variable(也叫類屬性):
?? ?類變量是類的屬性,此屬性屬于類
?? ?作用:用來記錄類的相關數據
?? ?說明:
?? ??? ?1、類變量可以通過類直接訪問
?? ??? ?2、類變量可以通過類的實例直接訪問
?? ??? ?3、類變量可以通過類的實例的__class__屬性訪問
?? ?實例:
?? ??? ?class Human:
?? ??? ??? ?count = 0 #創建類變量

class Human:count =0 #創建一個類變量 print("Human的類變量count=",Human.count)#0 h1 = Human() print("用h1對象訪問Human的count變量",h1.count)#0 print("用h1對象的__class__屬性訪問Human的count變量",h1.__class__.count)#0 h1.count = 100 #此處hi創建實例變量,通過實例不能通過這樣的方式修改類變量,可以通過__class__屬性來修改 print(h1.count) #100,會優先尋找實例變量,如果沒有實例變量才會訪問到類變量 print(Human.count) #0 print(h1.__class__.count) #0 View Code

??? 類變量的應用案例:
?? ??? ?用類變量來記錄對象的個數

class Car:count = 0def __init__(self,info):#創建類變量,用來記錄汽車對象的總數print(info,"被創建")self.data = info#記錄傳入的數據self.__class__.count +=1 #讓車的總數加1def __del__(self):print(self.data,"被銷毀")self.__class__.count -=1#讓車的總數減1 print("當前汽車總數是",Car.count) car1 = Car("奧迪") print(Car.count) car2 = Car("奔馳") car3 = Car("大眾") print(Car.count) View Code

類的文檔字符串:
?? ?類內的一個沒有賦值給任何變量的字符串是類的文檔字符串
?? ?說明:
?? ??? ?1、類的文檔字符串用類的__doc__屬性可以訪問
?? ??? ?2、類的文檔字符串可以用help()函數查看
類的__slots__列表:
?? ?作用:限定一個類的實例只能有固定的屬性(實例變量),通常為了防止錯寫屬性名而發生運行時錯誤
?? ?說明:含有__slots__列表的類創建的實例對象沒有__dict__屬性,即此實例不用字典來保存對象的屬性(實例變量)

class Student:__slots__ = ["name","score","aa"]#此處表示該實例對象最多只能有兩個實例變量def __init__(self,name,score):self.name = nameself.score = score s1 = Student("小張",58) print(s1.score) s1.socre = 100 #此處寫錯了屬性名,但在運行時不會報錯 ,如果添加了__slots__變量后就會產生AttributeError: 'Student' object has no attribute 'socre' print(s1.score) View Code

類方法 @classmethod
?? ?類方法是描述類的行為的方法,類方法屬于類
?? ?說明:
?? ??? ?1、類方法需要用@classmethod裝飾器定義
?? ??? ?2、類方法至少有一個形參,第一個形參用于綁定類,約定寫為‘cls’
?? ??? ?3、類和該類的實例都可以調用類方法
?? ??? ?4、類方法不能訪問此類創建的實例的屬性(只能訪問類變量)

class Car:count =0 #類變量 @classmethoddef getTotalCount(cls):'''此方法為類方法,第一個參數cls,代表調用此方法的類'''return cls.count@classmethoddef updateCount(cls,number):cls.count += number print(Car.getTotalCount())#用類來調用類方法 #Car.count += 1 #面向對象思想不提倡直接操作屬性 Car.updateCount(2) print(Car.getTotalCount())c1 = Car() c1.updateCount(100)#類的實例可以訪問類方法,是把c1.__class__傳給cls print(c1.getTotalCount()) View Code

問題:
?? ?1、類方法屬于類
?? ?2、實例方法屬于該類的實例
?? ?3、類內能不能有函數,既不屬于類又不屬于類的實例?
靜態方法 @staticmethos
?? ?靜態方法不屬于類,也不屬于類的實例,它相當于定義在類內的普通函數,只是它的作用域屬于類

class A:@staticmethoddef myadd(x,y):'''此方法為靜態方法,此方法的形參不需要傳入類或實例'''return x+y print("1+2=",A.myadd(1,2)) a = A() print("100+200=",a.myadd(100,200)) print(myadd(10,20))#NameError: name 'myadd' is not defined View Code

?繼承 inheritance 和? 派生? derived
?? ?什么是繼承/派生
?? ??? ?1、繼承是指從已有的類中衍生出新類,新類具有原有類的行為和屬性,并能擴展新的行為和屬性
?? ??? ?2、派生就是從一個已有類中衍生(創建)新類,在新類上可以添加新的屬性和行為
?? ?繼承和派生的目的:
?? ??? ?1、繼承是延續舊類的功能
?? ??? ?2、派生是為了在舊類的基礎上添加新的功能
?? ?作用:
?? ??? ?1、用繼承派生機制,可以將一些共有功能加在基類中,實現代碼的共享
?? ??? ?2、在不改變基類的基礎上改變原有的功能
?? ?繼承/派生的名詞:
?? ??? ?基類(base class),超類(super class),父類(father class)
?? ??? ?派生類(derived class),子類(child class)
?? ?單繼承:
?? ??? ?語法:class 類名( 基類名):
?? ??? ??? ??? ?語句塊
?? ??? ?說明:單繼承是指派生類由一個基類衍生出來的類
?? ?繼承說明:
?? ??? ?1、任何類都直接或間接的繼承自object類
?? ??? ?2、object類是一切類的超類(祖類)
?? ?類的__base__屬性:
?? ??? ?__base__屬性用來記錄此類的基類
?? ??? ?說明:類名.__base__ 返回的是繼承的第一個類
?? ?覆蓋 override:
?? ??? ?什么是覆蓋:
?? ??? ??? ?覆蓋是指在有繼承關系的類中,子類中實現了與基類同名的方法,在子類實例調用該方法時,實例調用的是子類中的覆蓋版本的方法,這種現象叫做覆蓋
?? ?問題:當覆蓋發生時,子類對象能否訪問父類中的方法?
?? ??? ?子類對象顯式調用基類方法的方式:
?? ??? ??? ?基類名.方法名(實例,實際調用傳參)
?? ??? ?super 函數:
?? ??? ??? ?super(type,obj) 返回綁定超類的實例
?? ??? ??? ?super() 返回綁定超類的實例,等同于:super(__class__,實例方法的第一個參數,必須在方法內調用)

def work(self):print("A.walk()被調用") class B(A):def work(self):print("B.walk()被調用")def super_work(self):#此處能調用超類的work方法#super(B,self).work() #A.walk()#super(__class__,self).work() #A.walk()被調用,在一個類內有一個__class__屬性,super().work() #A.walk(),在一個實例方法中__class__和self 都是已知的可以省略 b = B() b.work() # B.walk()被調用 b.__class__.__base__.work(b) #A.walk()被調用,使用顯式的方法調用超類的方法 super(B,b).work()#A.walk()被調用,super(B,b)返回的是B類的超類的對象實例 b.super_work() View Code

??? 顯示調用基類的初始化方法:
?? ??? ?當子類中實現了__init__方法時,基類的__init__方法并不會被調用,此時需要顯式調用

class Human():def __init__(self,n,a):self.name = nself.age = adef infos(self):print("姓名:",self.name)print("年齡",self.age) class Student(Human):def __init__(self,n,a,s):super().__init__(n,a)#使用超類中的__init__方法給name,age賦值self.score = ss1 = Student("小張",20,100) s1.infos() View Code

用于類的函數:
?? ?issubclass(cls,class_or_tuple):
?? ??? ?判斷一個類是否繼承自其它的類,如果此類cls是class或tuple中的一個派生子類則返回True,否則返回False
?? ?說明:cls是class的子類的子類...也返回True
查看python內建類的繼承關系的方法:
?? ?help(__bulitins__)
封裝 enclosure
?? ?1、封裝是指隱藏類的實現細節,讓使用者不用關心這些細節
?? ?2、封裝的目的是讓使用者盡可能少的使用實例變量(屬性)進行操作
私有屬性:
?? ?python類中,以雙下劃線“__”開頭的,不以雙下劃線結尾的標識符為私有成員,在類的外部無法直接訪問

class A:def __init__(self):self.__p1 = 100#__p1為私有屬性,在類的外部不能調用def test(self):print(self.__p1)#在類內可以調用私有屬性self.__m1() #A類的方法可以調用私有方法def __m1(self):'''我是私有方法,只有我自己的類的方法才能調用我'''print("我是A類的__m1方法") a = A() #print(a.__p1)#在類外看不到__p1屬性,訪問失敗 a.test() #a.__m1() #出錯,無法調用私有方法 View Code

多態 polymorphic
?? ?字面意思:“多種狀態”
?? ?多態是指在繼承/派生關系的類中,調用基類對象的方法,實際能調用子類的覆蓋版本方法的現象叫多態
?? ?說明:
?? ??? ?多態調用的方法與對象相關,不與類型相關
?? ??? ?Python的全部對象都只有“運行時狀態(動態)”,沒有“C++/Java”里的“編譯時狀態(靜態)”

class Shape():def draw(self):print("Shape.draw被調用") class Point(Shape):def draw(self):print("正在畫點") class Circle(Point):def draw(self):print("正在畫圓") def my_draw(s):s.draw() # 此處會調用誰的方法,此處顯示多態中的動態 s1 = Circle() s2 = Point() s3 = Shape() my_draw(s1)#正在畫圓 my_draw(s2)#正在畫點 my_draw(s3)#Shape.draw被調用 View Code

面向對象的編程語言的特征:
?? ?繼承
?? ?封裝
?? ?多態
?? ?如:C++(支持多繼承)/ Java /Python(支持多繼承)/Swift /C#
多繼承 multiple inheritance
?? ?多繼承是指一個子類繼承自兩個或兩個以上的基類
?? ?語法:
?? ??? ?class 類名(基類名1,基類名2....):
?? ??? ??? ?語句塊
?? ?說明:
?? ??? ?1、一個子類同時繼承自多個父類,父類中的方法可以同時被繼承下來
?? ??? ?2、如果兩個父類中有同名的方法,而在子類中又沒有覆蓋此方法時,調用結果難以確定
?? ?多繼承的問題(缺陷):
?? ??? ?標識符(名字空間沖突的問題)
?? ??? ??? ?要謹慎使用多繼承

class Car:def run(self,speed):print("汽車以",speed,"公里/小時的速度行駛") class Plane:def fly(self,height):print("飛機以海拔",height,"的高度飛行") class PlaneCar(Car,Plane):pass p1 = PlaneCar() p1.fly(10000) p1.run(300) View Code

多繼承的MRO(Method Resolution Order)問題:
?? ?類內的__mro__屬性用來記錄繼承方法的查找順序

class A:def m(self):print("A.m()被調用") class B:def m(self):print("B.m()被調用") class AB(A,B):pass ab = AB()#多繼承的調用方法,從左至右,,可以根據AB.__mro__來查看繼承的順序 ab.m() View Code class A:def m(self):print("A.m()") class B(A):def m(self):print("B.m()") class C(A):def m(self):print("C.m()") class D(B,C):def m(self):print("D.m()") d = D() print(D.__mro__)#(<class '__main__.D'>, <class '__main__.B'>, <class '__main__.C'>, <class '__main__.A'>, <class 'object'>) d.m()############################################################################################################################################ class A:def m(self):print("A.m()") class B(A):def m(self):print("B.m()")super().m()# 此處調用的是C類的方法,在多繼承中super()的窒執行順序是按照__mro__的順序來查找的 class C(A):def m(self):print("C.m()") class D(B,C):def m(self):print("D.m()")super().m()#此處調用B類的m方法 d = D() d.m() print(D.__mro__) # D.m() # B.m() # C.m() # (<class '__main__.D'>, <class '__main__.B'>, <class '__main__.C'>, <class '__main__.A'>, <class 'object'>)

函數重寫 override:
?? ?重寫是在自定義的類內添加相應(內建函數的方法)的方法,讓自定義的類生成的對象(實例)像內建對象一樣進行內建的函數操作

class MyNumber:pass n1 = MyNumber() x = len(n1) print(x) #TypeError: object of type 'MyNumber' has no len() ################################################################################### class MyNumber:def __len__(self):#重寫了len方法,重寫的必須是內建函數的方法return 10 n1 = MyNumber() x = len(n1) #相當于x = n1.__len__() print(x) #10 View Code

? 對象轉化為字符串函數重寫
?? ??? ?repr(obj)返回一個代表此對象的表達式字符串,通常:eval(repr(obj)) == obj
?? ??? ?str(obj)通過給定的對象返回一個字符串(這個字符串通常是給人看的)

class MyNumber:def __init__(self,value):self.data = value n1 = MyNumber(100) print(str(n1))#<__main__.MyNumber object at 0x7f676201cfd0>,相當于調用n1.__str__(self) print(repr(n1))#<__main__.MyNumber object at 0x7f676201cfd0>,相當于調用n1.__repr__(self) ######################################################################################### class MyNumber:def __init__(self,value):self.data = valuedef __str__(self):return "數字:%d" % self.datadef __repr__(self):return "MyNumber(%d)"% self.data n1 = MyNumber(100) print(str(n1))#數字:100,相當于調用n1.__str__(self) print(repr(n1))#MyNumber(100),相當于調用n1.__repr__(self) #n2 = eval(str(n1))#SyntaxError: invalid character in identifier n2 = eval(repr(n1))#可以創建n2對象實例 View Code

對象轉字符串函數的重寫方法:
?? ?repr()函數的重寫方法:
?? ??? ?def __repr__(self):
?? ??? ??? ?return 能夠表達self內容的字符串(可以通過eval()方法反推)
?? ?str()函數的重寫方法:
?? ??? ?def __str__(self):
?? ??? ??? ?return 人能看懂的字符串
?? ?說明:
?? ??? ?1、str(obj)函數優先調用obj.__str__()方法返回字符串
?? ??? ?2、如果obj沒有__str__()方法,則調用obj.__repr__()方法返回的字符串
?? ??? ?3、如果obj沒有__repr__()方法,則調用object類的__repr__()實例方法顯示<XXXXX>格式的字符串

   4、print(對象)相當于print(str(對象)),一個對象(實例)就是首先尋找__str__方法,在尋找__repr__方法
數值轉換函數的重寫:
?? ?def __complex__(self)?? ??? ?? complex(obj)函數調用
?? ?def __int__(self)?? ??? ??? ??? ? ? int(obj)函數調用
?? ?def __float__(self)?? ??? ??? ??? ?float(obj)函數調用
?? ?def __bool__(self)?? ??? ??? ??? ?bool(obj)函數調用

class MyNumber:def __init__(self,value):self.data = valuedef __repr__(self):print("__repr__被調用")return "MyNumber(%d)"% self.datadef __int__(self):'''此方法int(obj)函數重載,必須返回整數,此方法通常用于制定自定義對象如何轉為整數的規則'''return self.data n1 = MyNumber(100) print(type(n1))#<class '__main__.MyNumber'> n = int(n1) #相當于n1.__int__(self) print(type(n))#<class 'int'> print(n) View Code

內建函數的重寫:
?? ?__abs__??? ??? ??? ??? ??? ??? ? ?? abs(obj)
?? ?__len__?? ??? ??? ??? ??? ??? ??? ?? len(obj)
?? ?__reversed__?? ??? ??? ??? ??? ? reversed(obj)
?? ?__round__?? ??? ??? ??? ??? ??? ?? round(obj)

'''自定義一個MyList類,與系統內建的類一樣,用來保存有先后順序關系的數據''' class MyList():def __init__(self,iterator=[]):self.data = [x for x in iterator]def __repr__(self):return "MyList(%r)" % self.datadef __abs__(self):#return MyList([abs(x) for x in self.data])#上一句語句可以用如下生成器表達式代替以防止過多的占用內存return MyList((abs(x) for x in self.data))def __len__(self):return len(self.data) myl = MyList([1,-2,3,-4]) print(myl)#MyList([1, -2, 3, -4]) print(abs(myl))#MyList([1, 2, 3, 4]) print("原來的列表:",myl)#原來的列表: MyList([1, -2, 3, -4]),原來的列表 myl2 = MyList(range(10)) print("myl2的長度是:",len(myl2))#10 print("myl的長度是:",len(myl)) #4 View Code

布爾測試函數的重寫:
?? ?格式:def? __bool__(self):
?? ??? ??? ?   ....
?? ?作用:
?? ??? ?1、用于bool(obj)函數取值
?? ??? ?2、用于if語句真值表達式中
?? ??? ?3、用于while語句真值表達式中
?? ?說明:
?? ??? ?1、優先調用__bool__方法取值
?? ??? ?2、如果不存在__bool__方法,則用__len__()方法取值,后判斷是否為零值,如果不為零返回True,否則返回False
?? ??? ?3、如果再沒有__len__方法,則直接返回True

class MyList():def __init__(self,iterator=[]):self.data = [x for x in iterator]def __repr__(self):return "MyList(%r)" % self.datadef __abs__(self):#return MyList([abs(x) for x in self.data])#上一句語句可以用如下生成器表達式代替以防止過多的占用內存return MyList((abs(x) for x in self.data))def __len__(self):print("__len__方法被調用")return len(self.data) myl = MyList([1,-2,3,-4]) myl2 = MyList([]) print(bool(myl))# True print(bool(myl2))# False if myl2:#在此處會查找__bool__,如果沒有再查找__len__,再沒有直接返回Truepass while myl2:#在此處會查找__bool__,如果沒有再查找__len__,再沒有直接返回Truepass View Code

迭代器(高級):
?? ?什么是迭代器
?? ??? ?可以通過next(it)函數取值的對象就是迭代器
?? ?迭代器協議:
?? ??? ?迭代器協議是指對象能夠使用next函數獲取下一項數據,在沒有下一項數據是觸發StopIterator來終止迭代的約定
?? ?實現方法:
?? ??? ?類內需要有__next__(self)方法來實現迭代器協議
?? ?語法形式:
?? ??? ?class MyIterator:
?? ??? ??? ?def __next__(self):
?? ??? ??? ??? ?迭代器協議的實現
?? ??? ??? ??? ?return 數據
什么是可迭代對象:
?? ?1、是指能用iter(obj)函數返回迭代器的對象(實例)
?? ?2、可迭代對象內部一定要定義__iter__(self)方法來返回迭代器
可迭代對象的語法形式:
?? ?class MyIterable:
?? ??? ?def __iter__(self):
?? ??? ??? ?語句塊
?? ??? ??? ?return 迭代器

class MyList:def __init__(self,iterator):'''自定義列表的初始方法,此方法創建一個data實例變量來綁定一個用來存儲數據的列表'''self.data = list(iterator)def __repr__(self):'''此方法為了打印此列表的數據'''return 'MyList(%r)' % self.datadef __iter__(self):'''有此方法就是可迭代對象,但要求必須返回迭代器'''print("__iter__方法被調用")return MyListIterator(self.data) class MyListIterator:'''此類用來創建一個迭代器對象,用此迭代器對象可以迭代訪問MyList類型的數據'''def __init__(self,iter_data):self.cur = 0 #設置迭代器的初始值為0代表列表下標self.iter_data = iter_datadef __next__(self):'''有此方法的對象才叫迭代器',此方法一定要實現迭代器協議'''print("__next__方法被調用")if self.cur >= len(self.iter_data):raise StopIteration#否則尚未迭代完成,需要返回數據r = self.iter_data[self.cur]# 拿到要送回去的數據self.cur +=1 #將當前值向后移動一個單位return r myl = MyList([2,3,5,7]) print(myl) for x in myl:print(x) View Code

?對象的屬性管理函數:
?? ?1、getattr(obj,name[,dafault])?? ?從一個對象得到對象的屬性;gettattr(x,'y')等同于x.y;當屬性y不存在時,如果有default參數,則返回default,如果沒有給出default則產生一   個AttributeError錯誤
?? ?2、hasattr(obj,name)?? ? 用給定的name返回obj是否有屬性,如果有返回True,否則返回False,此種做法可以避免在getattr(obj,name)時引發錯誤
?? ?3、setattr(obj,name,value)? 給對象obj的名為name的屬性設置相應的值value,setattr(x,'y',v)等同于x.y = v
?? ?4、delattr(obj,name) 刪除對象obj中的name屬性,delattr(x,'y')等同于del x.y

class Car:def __init__(self,c,b):self.color = cself.brand = bdef get_car_attr(self,attr_name):'''此方法用于獲取對象的屬性,如果屬性在次對此對象中返回該屬性,如果不在時返回None'''return getattr(self,attr_name,None) c1 =Car("黑色",'Benz') v = c1.get_car_attr('color') if v is None:print("沒有顏色屬性") else:print("顏色是",v) View Code

運算符重載:
?? ?什么是運算符重載
?? ??? ?讓自定義的類生成的對象(實例)能夠使用運算符進行操作
?? ?作用:
?? ??? ?1、讓自定義的類的實例像內建對象一樣運行運算符操作
?? ??? ?2、讓程序簡潔易讀
?? ??? ?3、對自定義的對象,將運算符賦予新的運算規則


算術運算符的重載:
?? ?__add__(self, rhs)?? ??? ??? ?self +? rhs?? ??? ??? ? 加法
?? ?__sub__(self, rhs)?? ??? ??? ?self -? rhs?? ??? ??? ? 減法
?? ?__mul__(self, rhs)?? ??? ??? ?self *? rhs?? ??? ??? ? 乘法
?? ?__truediv__(self, rhs)?? ??? ?self /? rhs?? ??? ??? ? 除法
?? ?__floordiv__(self, rhs)?? ??? ?self // rhs?? ??? ??? ? 地板出法
?? ?__mod__(self, rhs)?? ??? ??? ?self %? rhs?? ??? ??? ? 求余
?? ?__pow__(self, rhs)?? ??? ??? ?self ** rhs?? ??? ??? ? 冪運算
?? ?注意:rhs(right hands side )右手邊

class MyNumber:def __init__(self,v):self.data = vdef __repr__(self):return "MyNumber(%)" % self.data# def myadd(self,other):# v = self.data + other.data# return MyNumber(v)def __add__(self,other):v = self.data + other.datareturn MyNumber(v)def __sub__(self,other):v = self.data - other.datareturn MyNumber(v) n1 = MyNumber(100) n2 = MyNumber(200) #n3 = n1.myadd(n2) n3 = n1 + n2 # 等同于n1.__add__(n2) print(n3)#MyNumber(300) n4 = n3 - n2 #等同于n3.__sub__(n2) print(n4) #MyNumber(100) View Code

反向算數運算符的重載:
?? ?當左手邊的類型為內建類型,右手邊為自定義類型時,要實現運算必須用以下方法重載
?? ?__radd__(self, lhs)?? ??? ??? ?lhs +? self?? ??? ??? ? 加法
?? ?__rsub__(self, lhs)?? ??? ??? ?lhs -? self?? ??? ??? ? 減法
?? ?__rmul__(self, lhs)?? ??? ??? ?lhs *? self?? ??? ??? ? 乘法
?? ?__rtruediv__(self, lhs)?? ??? ?lhs /? self?? ??? ??? ? 除法
?? ?__rfloordiv__(self, lhs)?? ?lhs // self?? ??? ??? ? 地板出法
?? ?__rmod__(self, lhs)?? ??? ??? ?lhs %? self?? ??? ??? ? 求余
?? ?__rpow__(self, lhs)?? ??? ??? ?lhs ** self?? ??? ??? ? 冪運算

'''實現兩個自定義列表相加''' class MyList():def __init__(self,iterable):self.data = iterabledef __repr__(self):return 'MyList(%s)' % self.data def __mul__(self,rhs):v = self.data * rhsreturn MyList(v)def __add__(self,other):v = self.data +other.datareturn MyList(v)def __rmul__(self,lhs):return MyList(self.data*lhs)def __iadd__(self,other):self.data.extend(other.data)#此出是改變self本身,返回值為Nonereturn self L1 = MyList([1,2,3]) L2 = MyList([4,5,6]) L3 = L1 + L2 #等同于L1.__add__(L2) print(L3)#MyList([1, 2, 3, 4, 5, 6]) L4 = L2 + L1 print(L4)#MyList([4, 5, 6, 1, 2, 3]) L5 = L1 * 2 #等同于L1.__mul__(2) print(L5)#MyList([1, 2, 3, 1, 2, 3]) #(反方算數運算符)當左手邊的類型為內建類型,右手邊為自定義類型時,要實現運算必須用一下方法重載 L6 = 2* L1 print(L6)#MyList([1, 2, 3, 1, 2, 3]) #符合算數運算符: L1 += L2 #當沒有__iadd__方法時,等同于調用L1 = L1 + L2,在這里又重新創建了一個MyList類的對象 print(L1)#當有__iadd__方法時,在這里不會重新創建了一個MyList類的對象,而是在L1實例上改變 View Code

符合賦值運算符的重載:
?? ?__iadd__(self, rhs)?? ??? ??? ?self +=? rhs?? ??? ??? ? 加法
?? ?__isub__(self, rhs)?? ??? ??? ?self -=? rhs?? ??? ??? ? 減法
?? ?__imul__(self, rhs)?? ??? ??? ?self *=? rhs?? ??? ??? ? 乘法
?? ?__itruediv__(self, rhs)?? ??? ?self /=? rhs?? ??? ??? ? 除法
?? ?__ifloordiv__(self, rhs)?? ?self //= rhs?? ??? ??? ? 地板出法
?? ?__imod__(self, rhs)?? ??? ??? ?self %=? rhs?? ??? ??? ? 求余
?? ?__ipow__(self, rhs)?? ??? ??? ?self **= rhs?? ??? ??? ? 冪運算
比較運算符的重載:
?? ?__lt__(self,rhs)?? ??? ??? ?self <?? rhs?? ??? ??? ? 小于
?? ?__le__(self,rhs)?? ??? ??? ?self <=? rhs?? ??? ??? ? 小于等于
?? ?__gt__(self,rhs)?? ??? ??? ?self >?? rhs?? ??? ??? ? 大于
?? ?__ge__(self,rhs)?? ??? ??? ?self >=? rhs?? ??? ??? ? 大于等于
?? ?__eq__(self,rhs)?? ??? ??? ?self ==? rhs?? ??? ??? ? 等于
?? ?__ne__(self,rhs)?? ??? ??? ?self !=? rhs?? ??? ??? ? 不等于
?? ?注:比較運算符通常返回True 或 False
?? ??? ?lt:less than??????? le:less or equal
?? ??? ?gt:greater than?? ??? ?gt:gerater or equl
?? ??? ?eq:equal?? ??? ??? ?ne:not equal
位運算符重載:
?? ?__invert__(self)?? ??? ??? ?~ self?? ??? ??? ??? ??? ?取反(一元運算符)
?? ?__and__(self,rhs)?? ??? ??? ?self? & rhs?? ??? ??? ??? ?位與
?? ?__or__(self,rhs)?? ??? ??? ?self? | rhs?? ??? ??? ??? ?位或
?? ?__xor__(self,rhs)?? ??? ??? ?self? ^ rhs?? ??? ??? ??? ?位異或
?? ?__lshift__(self,rhs)?? ??? ?self? << rhs?? ??? ??? ?左移
?? ?__rshift__(self,rhs)?? ??? ?self? >> rhs?? ??? ??? ?右移
反向位運算符重載:
?? ?__rand__(self,lhs)?? ??? ??? ?lhs? & self?? ??? ??? ??? ?位與
?? ?__ror__(self,lhs)?? ??? ??? ?lhs? | self?? ??? ??? ??? ?位或
?? ?__rxor__(self,lhs)?? ??? ??? ?lhs? ^ self?? ??? ??? ??? ?位異或
?? ?__rlshift__(self,lhs)?? ??? ?lhs << self?? ??? ??? ??? ?左移
?? ?__rrshift__(self,lhs)?? ??? ?lhs >> self?? ??? ??? ??? ?右移
?? ?注:當左手邊的類型為內建類型,右手邊為自定義類型時,使用反向位運算符重載
復合賦值位運算符:
?? ?__iand__(self,lhs)?? ??? ??? ?lhs? &= self?? ??? ??? ??? ?位與
?? ?__ior__(self,lhs)?? ??? ??? ?lhs? |= self?? ??? ??? ??? ?位或
?? ?__ixor__(self,lhs)?? ??? ??? ?lhs? ^= self?? ??? ??? ??? ?位異或
?? ?__ilshift__(self,lhs)?? ??? ?lhs <<= self?? ??? ??? ??? ?左移
?? ?__irshift__(self,lhs)?? ??? ?lhs >>= self?? ??? ??? ??? ?右移
一元運算符的重載:
?? ?__neg__(self)?? ??? ??? ??? ?- self?? ??? ??? ??? ??? ??? ?負號
?? ?__pos__(self)?? ??? ??? ??? ?+ self?? ??? ??? ??? ??? ??? ?正號
?? ?__invert__(self)?? ??? ??? ?~ self?? ??? ??? ??? ??? ??? ?取反
?? ?一元運算符的重載方法:
?? ??? ?class 類名:
?? ??? ??? ?def __XXX__(self):
?? ??? ??? ??? ?....

class MyList():def __init__(self,iterable):print("__init__被調用")self.data = iterabledef __repr__(self):return 'MyList(%r)' % self.data def __neg__(self):'''此方法用來制定 - self 返回的規則'''L = (-x for x in self.data)return MyList(L) L1 = MyList([1,-2,3,-4]) L2 = -L1 print(L2)#MyList([-1, 2, -3, 4]) View Code

運算符重載說明:
?? ?運算符重載不能改變運算符的優先級
python類名最好用駝峰命名法:
?? ?MyList?? MyRange?? ??? ?大駝峰(所有單詞首字母大寫,其余小寫)
?? ?getStudentAge?? ??? ??? ?小駝峰(第一個單詞首字母小寫,其他首字母大寫)


in /not in 運算符的重載:
?? ?重載方法:
?? ??? ?def __contanins__(self,e)?? ??? ?e in self???? 成員運算

class MyList():def __init__(self,iterable):self.data = iterabledef __repr__(self):return 'MyList(%r)' % self.data def __contains__(self,e):'''此方法用來實現 in /not in 運算符的重載'''print("__contains__被調用")for x in self.data:if x == e:return Truereturn False L1 = MyList([1,-2,3,-4]) if -2 in L1:print("-2在L1中") else:print("-2不在L中") #當MyList的類內重載了__contains__方法,則not in 也同時可以使用(將__contains__方法的返回值取反) if 5 not in L1:print("5不在L1中") else:print("-5在L中") View Code

索引和切片運算符的重載:
?? ?__getitem__(self,i)?? ??? ?x = self[i]?? ??? ?索引和切片取值
?? ?__setitem__(self,i,v)?? ?self[i] = v???? 索引和切片賦值
?? ?__delitem__(self,i)?? ??? ?del self[i]?? ??? ?del 語句刪除索引
?? ?作用:讓自己定義的類型的對象能夠支持索引和切片操作
slice函數:
?? ?作用:用于創建一個Slice切片對象,此對象存儲一個切片的起始值,終止值和步長信息
?? ?slice(start,stop=None,step=None) 創建一個切片對象
?? ?slice的對象的屬性:
?? ??? ?s.start?? ??? ??? ??? ?切片的起始值,默認為None
?? ??? ?s.stop?? ??? ??? ??? ?切片的終止值,默認為None
?? ??? ?s.step?? ??? ??? ??? ?切片的步長,默認為None

class MyList():def __init__(self,iterable):print("__init__被調用")self.data = iterabledef __repr__(self):return 'MyList(%r)' % self.data def __getitem__(self,i):print("__getitem__被調用,i=",i)if type(i) is not int:raise TpyeErrorreturn self.data[i]def __setitem__(self,i,v):self.data[i] = v L1 = MyList([1,-2,3,-4]) v = L1[1] print(v)#-2 L1[1] = 2 print(L1)#MyList([1, 2, 3, -4]) View Code class MyList():def __init__(self,iterable):print("__init__被調用")self.data = iterabledef __repr__(self):return 'MyList(%r)' % self.data def __getitem__(self,i):print("__getitem__被調用,i=",i)if type(i) is int:print("正在做索引操作")elif type(i) is slice:print("正在做切片操作")print("起始值:",i.start)print("終止值:",i.stop)print("步長:",i.step)else:raise KeyErrorreturn self.data[i]L1 = MyList([1,-2,3,-4,5,-6])print(L1[::2])#等同于調用L1[slice(None,None,2)] # __init__被調用 # __getitem__被調用,i= slice(None, None, 2) # 正在做切片操作 # 起始值: None # 終止值: None # 步長: 2 # [1, 3, 5] View Code

?類的特殊成員

  1、__call__()方法

class Foo:def __init__(self):print("init")def __call__(self):print("call")Foo()()#首先會執行__init__()方法,再執行__call__()方法 obj = Foo()#執行__init__()方法 obj()#執行__call__()方法

?metaclass(類的祖宗)

  1、Python中一切事物都是對象

  2、class Foo:

      pass

    obj = Foo()

    #obj是對象,Foo類的對象

    #Foo類也是一個對象,type的對象

  3、類都是type類的對象,type(...)

def function(self):print("hello world") #創建一個Foo類繼承object,含有func()方法 Foo = type("Foo",(object,),{'func':function}) obj = Foo()obj.func()

?

class MyType(type):def __init__(self,*args,**kwargs):super().__init__(*args,**kwargs)#執行父類type的__init__方法print("MyType的__init__")def __call__(self):print("MyType的__call__")obj = self.__new__(self)#self代表Foo,第三步調用Foo中的new方法,返回Foo的對象self.__init__(obj)#第四步調用Foo中的__init__方法class Foo(object,metaclass=MyType):#第一步,編譯器執行到此處是會調用MyType的__init__方法def __init__(self):print("Foo的__init__")def __new__(cls,*args,**kwargs):print("Foo中的__new__方法")return object.__new__(cls,*args,**kwargs)#真正創建Foo類的對象的地方 obj = Foo()#第二步,在Foo類(MyTpye類的對象)加(),會執行MyType中的__call__方法

?

?

?

?

?

  

轉載于:https://www.cnblogs.com/xdl-smile/p/9346948.html

總結

以上是生活随笔為你收集整理的python_面向对象的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。