給自己的Python小筆記: Class 設計(下) - Matters

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

Github連結6. Static Method, Class Method, Abstract Method1.簡單來說: Static 與Class 都可以當成是存取類別屬性的方法,他們不需要建立實體 ... Pythonpython給自己的Python小筆記:Class設計(下)2020年9月1日分佈式入口Github連結6.StaticMethod,ClassMethod,Abstract Method1.簡單來說: Static與Class都可以當成是存取類別屬性的方法,他們不需要建立實體物件(instance),也就是前面章節提到的實體屬性,它就使用,那他們有什麼差異呢,class需要多帶一個cls的參數才能使用,而static不用2.簡單比較一下:a.StaticMethod:靜態的方法,不需要建立instance,也不需要帶一個cls當參數b.ClassMethod:類方法,不需要建立instance,需要帶一個cls當參數c.AbstractMethod:抽象方法,還沒被實際create出來,它繼承class(類),要用覆寫的方式來實作3.Static與Class :我這邊實作一個同時包含class與static方法,他們做的事情一模一樣,只是一個讓類別屬性加1,另一個加2,可以從這邊看出都是要改變類別屬性的值,兩者的時作方法差異a.StaticMethod:在funtion前面加上@staticmethodb.ClassMethod:在function前面加上@classmethod,並且帶入一個參數clsclassHouse: tv_amount=1#類別屬性 def__init__(self,human,name): self.human=human##實體屬性 self.name=name##實體屬性 House.add_tv(1)##static House.add_tv1(2)##class @staticmethod defadd_tv(i): House.tv_amount+=i @classmethod defadd_tv1(cls,i): cls.tv_amount+=i little_turtle_home=House(1,"Turtle") print(little_turtle_home.name)#Turtle print(little_turtle_home.human)#1 print(little_turtle_home.tv_amount)#4 print(House.tv_amount)#4 little_turtle_home1=House(1,"Turtle") print(little_turtle_home1.tv_amount)#7 print(House.tv_amount)#7 4.AbstractMethod:就跟它的名字一樣,它是一個抽象的類,很抽象所以不能實例化(instance),它只能被子類別繼承a.首先我們先導入一個package:impotabc,很特別的名字b.再來,在我們想要抽象化的類裡面的參數,寫入abc.ABC或metaclass=abc.ABCMeta,就將它抽象化了c.抽象類裡面的function必須前面加上@abc.abstractmethodd.欲繼承的子類別,要在類參數裡寫入父類別的名稱e.記得:繼承這個抽象類的子類別,必須有抽象類裡面的function,不然會出現錯誤,這個時候你就要再將這些function補上我這邊就來實作一個抽象老烏龜,被兩隻小烏龜繼承,一隻有繼承swim,一隻沒有,結果沒有的就印不出來,原因就是沒有繼承父類別(抽象類別)的function##importabstractpackage importabc classold_Turtle(abc.ABC): @abc.abstractmethod defswim(self): print('Icanswim') returnNotImplemented classyoung_turtle(old_Turtle): defswim(self): print('Icanswimfast') defeat(self): print('Icaneat') classlittle_turtle(old_Turtle): defeat(self): print('Icaneat') print(young_turtle().swim())#Icanswimfast print(young_turtle().eat())#Icaneat print(little_turtle().eat())#TypeError:Can'tinstantiateabstractclasslittle_turtlewithabstractmethodsswim 7.類別封裝(Encapsulation)1.目的:很簡單,就是過往我們在Class裡面的屬性都是門戶洞開的,任何人都能輕易看到裡面的內容,但是我們有時候想要一點隱私(private),就是不想被別人輕鬆看見,所以我們要用封裝的方法,將屬性隱藏起來,但我們自己要讀,所以我們要用別的方式讀取這些屬性內容 2.怎麼做:我們只要將想要隱藏的屬性是別字加上__(兩個底線)就能輕鬆實現舉例:classHouse: def__init__(self,address,name,phone_number): self.__address=address self.__name=name self.phone_number=phone_number self.member=0 little_turtle_home=House('anyTownanyStreet','Turtle','09xx') print(little_turtle_home.phone_number)##沒封裝:09xx print(little_turtle_home.__address)##有封裝:AttributeError:'House'objecthasnoattribute'address' 看不到了!!3.但是我們總是要自己看吧,所以要在function寫一個能獲取這個attribute(屬性)的方法舉例:classHouse: def__init__(self,address,name,phone_number): self.__address=address self.__name=name self.phone_number=phone_number self.member=0 defget_attribute(self): returnself.__address little_turtle_home=House('anyTownanyStreet','Turtle','09xx') print(little_turtle_home.phone_number)##沒封裝:09xx #print(little_turtle_home.address)##有封裝:AttributeError:'House'objecthasnoattribute'address' print(little_turtle_home.get_attribute())##有封裝,但換個方法get起來:anyTownanyStreet 8.Class中再定義一個Class這邊我們來看看一個特別的情況,在Class中再定義一個Class,我們先定義一個Class(House),並在裡面再建立另一個Class(material),這邊先建立一個little_turtle_home(),接著建立一個新家new_little_turtle_home使用brick(new_little_turtle_home=little_turtle_home.material(“brick”)),當我們的material(class)從範例中,可以看到我們定義了另一個class來存放material資訊,然後我們來看看如何使用這個新的Class##建立一個Class classHouse: def__init__(self,address,name,phone_number): self.address=address self.name=name self.phone_number=phone_number ##再建立一個class classmaterial: def__init__(self,material): self.material=material deffind(self): return"findoutmaterial!!" ##先建立一個little_turtle_home little_turtle_home=House('anyTownanyStreet','Turtle','09xx') ##再建立一個在little_turtle_home底下的class new_little_turtle_home=little_turtle_home.material("brick") ##使用這個class的function print(new_little_turtle_home.find())#findoutmaterial!! ##查看Houseclass底下的資訊 print(little_turtle_home.address,little_turtle_home.name,little_turtle_home.phone_number,end='')#anyTownanyStreetTurtle09xx ##在House底下建立個另一個classmaterial,沒辦法用它查看外層classHouse的資訊 #print(new_little_turtle_home.address,new_little_turtle_home.name,new_little_turtle_home.phone_number)#'material'objecthasnoattribute'address' ##使用這個class的屬性 print(new_little_turtle_home.material)#brick ##查看原本建立的classlittle_turtle_home底下的classmaterial print(little_turtle_home.material)# 9.新增參數與__slots__(不給新增參數)用法a.我們可以透過.來直接賦予新的參數值給類(Class),格式:(class).(variablename)=‘(newvalue)’,Little_turtle_home.name=‘Turtle’b.pass:順便一提,它是為了維持結構的完整性classHouse(object): pass Little_turtle_home=House() Little_turtle_home.name='Turtle'##賦予新值 print(Little_turtle_home.name)#Turtle c.__slot__ :在Class中,寫下這個時,會沒辦法賦值,只有__slot__={},dict裡面的可以賦予值舉例:如果跟剛剛一樣賦予一個值給name,Little_turtle_home1.name=‘Turtle’,這邊就會報錯,但是如果你賦予的值是__slot__={}裡面有的,就可以執行,Little_turtle_home1.phone=‘09xx’classHouse(object): pass Little_turtle_home=House() Little_turtle_home.name='Turtle'##賦予新值 print(Little_turtle_home.name)#Turtle classHouse1(object): __slots__={'people_amount','phone'} pass Little_turtle_home1=House1() #Little_turtle_home1.name='Turtle'#'House1'objecthasnoattribute'name' Little_turtle_home1.people_amount=1 print(Little_turtle_home1.people_amount)#1 Little_turtle_home1.phone='09xx' print(Little_turtle_home1.phone)#09xx 希望對您有幫助!!Reference:https://blog.louie.lu/2017/07/28/你所不知道的-python-標準函式庫用法-03-abc/https://www.maxlist.xyz/2019/12/08/python-class-static-abstract-method/https://chenhh.gitbooks.io/parallel_processing/cython/python_class.html支持作者喜歡我的文章嗎?別忘了給點支持與讚賞,讓我知道創作的路上有你陪伴。

CCBY-NC-ND2.0版權聲明25看不過癮?一鍵登入,即可加入全球最優質中文創作社區登入



請為這篇文章評分?