python內部有許多內建裝飾器,它們都有特別的功能,下面對其歸納一下。
系列文章
python設計模式之單例模式(一)
python設計模式之常用建立模式總結(二)
python設計模式之裝飾器詳解(三)
python設計模式之內建裝飾器使用(四)
python設計模式之迭代器與產生器詳解(五)
python裝飾器介紹
- 參考:www.cnblogs.com/cwp-bg/p/9547797.html
python內建裝飾器staticmethod
staticmethod裝飾器的功能是去除類的方法預設第一個參數是類的執行個體,使得該方法成為一個普通的函數,staticmethod是一個類,屬於類裝飾器。
class Person(object): def eat(self): print('eat thing') @staticmethod def go(): # 不再傳遞self print('go')
classmethod
類定義時,內部的方法預設是類的執行個體對象的方法,classmethod裝飾器使得定義的方法變成類方法,類方法的第一個參數是類本身;調用類方法不需要建立類的執行個體。classmethod也是一個類,所以classmethod是一個類裝飾器。
class Person(object): _num_ear = 2 def eat(self): print('eat thing') @classmethod def go(cls): print(cls._num_ear) print('go')if __name__ == '__main__': Person.go() # 無需建立執行個體,直接調用。
property
對於一個類的屬性,python的訪問是沒有限制的,但有時候我們需要對屬性的訪問加以限制,property裝飾器就是幹這個的。
property是一個類,它有三個方法,deleter,setter,getter,有兩種使用方式。
class Person(Animal): _num_ear = 2 def __init__(self): self._name = 'xiaoming' self.age = 20 def get_name(self): print('get name') return self._name def set_name(self, name): print('set name') self._name = name def delete_name(self): print('del name') del self._name name = property(get_name, set_name, delete_name, doc='name of person')if __name__ == '__main__': p = Person() print(p.name) # 會調用get_name p.name = 'xxxx' # 會調用set_name del p.name # 會調用delete_name
property可以手動指定限制的函數,有四個參數,但是這樣顯得比較麻煩,可以使用裝飾器的形式。
class Person(Animal): _num_ear = 2 @property def name(self): return self._name @name.setter def name(self, nm): self._name = nm @name.deleter def name(self): del self._nameif __name__ == '__main__': p = Person() print(p.name) p.name = 'xxxx' del p.name
一個函數被property裝飾後返回的是property對象,只有fget參數的函數可以被property,因為裝飾器只接受一個參數;另外的屬性設定和刪除需要直觀調用響應的方法。
abstractmethod
python的抽象類別和java不一樣,java的抽象類別不能執行個體化,同時抽象方法子類必須實現,否則報錯!但是python抽象類別預設是可以執行個體化的,也可以這樣說,如果我們對抽象類別定義:本身不能執行個體化,子類必須實現抽象方法;那麼我們一般寫的基類都不是抽象類別。如果想要實現java中的抽象類別的效果該怎麼辦呢?使用abstractmethod裝飾器,含義是抽象方法。
一個類中的任何方法被abstractmethod裝飾後,這個類不能執行個體化並且子類必須實現被abstractmethod裝飾的方法。
from abc import abstractmethod,ABCMetaclass Animal(metaclass=ABCMeta): @abstractmethod def eat(self): passclass Person(Animal): _num_ear = 2 def eat(self): print('eat thing') @classmethod def go(cls): print(cls._num_ear) print('go')
如果需要定義一個類是抽象類別,那麼它需要繼承ABCMeta而不是object,這樣abstractmethod裝飾器才會起作用。其起作用的原理是將一個方法的__isabstractmethod__屬性設定為True,這樣解譯器就會檢查子類是否實現了抽象方法。