python?@property?裝飾器使用方法
一、property的裝飾器用法
先簡(jiǎn)單上個(gè)小栗子說(shuō)明:
class property(fget=None,fset=None,fdel=None,doc=None)
fget是用于獲取屬性值的函數(shù)fset是用于設(shè)置屬性值的函數(shù)fdel是用于刪除屬性值的函數(shù)doc為屬性對(duì)象創(chuàng)建文檔字符串
使用property可以講類的方法變成同名屬性,使用起來(lái)更加簡(jiǎn)潔,最后實(shí)例展示
使用時(shí)建議直接用property的裝飾器用法, 比較簡(jiǎn)潔,下面是官方示例,利用@property裝飾方法x將其變成名稱相同的屬性, 通過(guò)fget, fset, fdel可以控制x的讀寫(xiě)刪屬性.
class C:
def __init__(self):
self._x = None
@property
def x(self):
"""I'm the 'x' property."""
return self._x
#設(shè)置fset,注意x要與@property修飾的方法名稱相同
@x.setter
#這個(gè)fset名稱沒(méi)有限制,建議與x相同
def x(self, value):
self._x = value
#設(shè)置fdel
@x.deleter
def x(self):
del self._x話不多說(shuō), 直接上例子, 在Man這個(gè)類中設(shè)置一個(gè)可讀可寫(xiě)的birthYear屬性,一個(gè)可讀gender屬性,一個(gè)可讀可寫(xiě)可刪的體重屬性,還有一個(gè)利用birthYear推算出的age屬性
""" @property, @*.setter"""
from datetime import datetime
class Man:
def __init__(self, birthYear=None, gender=None, weight=None):
"""1.使用@property可以隱藏私有屬性,例如把'_birthYear'屬性隱藏,
把property對(duì)象birthYear作為對(duì)外的屬性"""
self._birthYear = birthYear
self._gender = gender
self._weight = weight
@property
def birthYear(self):
return self._birthYear
@birthYear.setter
def birthYear(self, value):
"""2.可以在setter中對(duì)屬性輸入進(jìn)行限制或者其他操作"""
assert not value > datetime.now().year, f'please input the right value!'
self._birthYear = value
@property
"""3.獲取年齡直接用obj.age,而不需寫(xiě)成方法obj.age(), 更加自然方便"""
def age(self):
return datetime.now().year - self._birthYear
@property
def gender(self):
return self._gender
@property
def weight(self):
return self._weight
@weight.setter
def weight(self, value):
self._weight = value
@weight.deleter
def weight(self):
del self._weight
lilei = Man(1996, 'male', 180)
age = lilei.age
print('Lilei今年{}歲\n'.format(age))
# 設(shè)置性別
try:
lilei.gender = 'female'
except:
print('性別無(wú)法進(jìn)行更改!\n')
# 更新體重
print(f'lilei減肥前的體重:{lilei.weight}\n')
lilei.weight = 200
print(f'lilei減肥后的體重:{lilei.weight}\n')
print('lilei減肥失敗后一氣之下將體重信息刪了\n')
del lilei.weight
try:
print('lilei的體重{}'.format(lilei.weight))
except:
print('找不到lilei的體重信息!')輸出結(jié)果:
Lilei今年25歲
性別無(wú)法進(jìn)行更改!
lilei減肥前的體重:180
lilei減肥后的體重:200
lilei減肥失敗后一氣之下將體重信息刪了
找不到lilei的體重信息!
二、舉例說(shuō)明
現(xiàn)在讓我們直觀看一下python內(nèi)置property修飾器為什么會(huì)存在,可以用來(lái)解決什么問(wèn)題?
先來(lái)一個(gè)具體的例子,定義一個(gè)表示攝氏度的class并且這個(gè)類包含一個(gè)從攝氏度轉(zhuǎn)換到華氏溫度的方法。
1.不用setter和getter方法的實(shí)現(xiàn)
# 初始版本
class Celsius:
def __init__(self, temperature = 0):
self.temperature = temperature
def to_fahrenheit(self):
return (self.temperature * 1.8) + 32
# 實(shí)例化
human = Celsius()
# 設(shè)置溫度
human.temperature = 37
# 獲取溫度值
print(human.temperature)
# 調(diào)用內(nèi)置方法將攝氏度轉(zhuǎn)化為華氏溫度
print(human.to_fahrenheit())輸出結(jié)果:
37
98.60000000000001
2.使用setter和getter的實(shí)現(xiàn),增加溫度值輸入的限制
但是如果現(xiàn)在有人讓human.temperature = -300 , 我們知道攝氏溫度是不可能低于-273.15的,此時(shí)需要對(duì)溫度值進(jìn)行限制, 常規(guī)方法是設(shè)置一個(gè)溫度值的setter和getter的方法,此時(shí)溫度值存放在_temperature 中
# 更新溫度限制的版本
class Celsius:
def __init__(self, temperature=0):
self.set_temperature(temperature)
def to_fahrenheit(self):
return (self.get_temperature() * 1.8) + 32
# getter method
def get_temperature(self):
return self._temperature
# setter method
def set_temperature(self, value):
if value < -273.15:
raise ValueError("攝氏溫度不可能低于 -273.15 !")
self._temperature = value
# 實(shí)例化
human = Celsius(37)
# 使用添加的getter獲取溫度值
print(human.get_temperature())
# 調(diào)用內(nèi)置方法將攝氏度轉(zhuǎn)化為華氏溫度
print(human.to_fahrenheit())
# 使用添加的setter對(duì)溫度值進(jìn)行設(shè)置
human.set_temperature(-300)
# Get the to_fahreheit method
print(human.to_fahrenheit())毫無(wú)疑問(wèn),在設(shè)置溫度值等于-300的時(shí)候肯定會(huì)報(bào)錯(cuò),但是這個(gè)時(shí)候你可能發(fā)現(xiàn)設(shè)置和獲取溫度值的代碼發(fā)生變化而且更復(fù)雜 并且 你需要對(duì)Celsius類的初始化函數(shù)進(jìn)行更改,self.temperature = temperature到 self.set_temperature(temperature), 如果現(xiàn)在是一個(gè)擁有很多屬性的類, 一個(gè)一個(gè)去進(jìn)行這樣的更改是很麻煩的,而且可能會(huì)導(dǎo)致與這個(gè)類別相關(guān)的代碼出現(xiàn)錯(cuò)誤, 有沒(méi)有更好的實(shí)現(xiàn)方式呢?這個(gè)時(shí)候就該今天的主角property裝飾器出場(chǎng)了
3.利用property裝飾器實(shí)現(xiàn)的版本
# 使用 @property 裝飾器版本
class Celsius:
def __init__(self, temperature=0):
#這里的self.temperture是下面定義的property對(duì)線 temperatue
#所以你會(huì)發(fā)現(xiàn)在初始化Celsius時(shí), 調(diào)用了temperature.setting方法
self.temperature = temperature
def to_fahrenheit(self):
return (self.temperature * 1.8) + 32
@property
def temperature(self):
print("獲取溫度值...")
return self._temperature
@temperature.setter
def temperature(self, value):
print("設(shè)置溫度值...")
if value < -273.15:
raise ValueError("攝氏溫度不可能低于 -273.15 !")
self._temperature = value
# 用property的實(shí)現(xiàn)后獲取和設(shè)置溫度值與最初的版本一樣!
human = Celsius()
# 設(shè)置溫度
human.temperature = 37
# 獲取溫度值
print(human.temperature)
# 調(diào)用內(nèi)置方法將攝氏度轉(zhuǎn)化為華氏溫度
print(human.to_fahrenheit())
#測(cè)試溫度限制功能
human.temperature = -300輸出結(jié)果:
設(shè)置溫度值...
設(shè)置溫度值...
獲取溫度值...
37
獲取溫度值...
98.60000000000001
設(shè)置溫度值...
---------------------------------------------------------------------------
ValueError Traceback (most recent call last)
d:\2.github\python_demo\016_decorator.py in <module>
30
31 #測(cè)試溫度限制功能
---> 32 human.temperature = -300d:\2.github\python_demo\016_decorator.py in temperature(self, value)
16 print("設(shè)置溫度值...")
17 if value < -273.15:
---> 18 raise ValueError("攝氏溫度不可能低于 -273.15 !")
19 self._temperature = value
20ValueError: 攝氏溫度不可能低于 -273.15 !
可以看到此時(shí)temperature設(shè)置有限制而且獲取和設(shè)置溫度值的代碼與初始版本一模一樣,也就是說(shuō)代碼可以向后兼容
到此這篇關(guān)于python @property 裝飾器使用詳細(xì)的文章就介紹到這了,更多相關(guān)python @property 裝飾器內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
分析運(yùn)行中的 Python 進(jìn)程詳細(xì)解析
這篇文章主要介紹了分析運(yùn)行中的 Python 進(jìn)程,本文給大家介紹的非常詳細(xì),具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2019-06-06
django框架事務(wù)處理小結(jié)【ORM 事務(wù)及raw sql,customize sql 事務(wù)處理】
這篇文章主要介紹了django框架事務(wù)處理,結(jié)合實(shí)例形式總結(jié)分析了使用ORM 事務(wù)及raw sql,customize sql 事務(wù)處理相關(guān)實(shí)現(xiàn)技巧與操作注意事項(xiàng),需要的朋友可以參考下2019-06-06
三步解決python PermissionError: [WinError 5]拒絕訪問(wèn)的情況
這篇文章主要介紹了三步解決python PermissionError: [WinError 5]拒絕訪問(wèn)的情況,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2020-04-04
python中?OpenCV和Pillow處理圖像操作及時(shí)間對(duì)比
這篇文章主要介紹了python中OpenCV和Pillow處理圖像操作及時(shí)間對(duì)比,文章圍繞主題展開(kāi)詳細(xì)的內(nèi)容介紹,具有一定的參考價(jià)值,需要的小伙伴可以參考一下2022-09-09
利用Python內(nèi)置庫(kù)實(shí)現(xiàn)創(chuàng)建命令行應(yīng)用程序
Python?有一個(gè)叫做argparse的內(nèi)置庫(kù),可以用它來(lái)創(chuàng)建一個(gè)命令行界面。本文將詳解如何利用argparse實(shí)現(xiàn)創(chuàng)建一個(gè)命令行應(yīng)用程序,需要的可以參考一下2022-06-06
python批量設(shè)置多個(gè)Excel文件頁(yè)眉頁(yè)腳的腳本
這篇文章主要介紹了python批量設(shè)置多個(gè)Excel文件頁(yè)眉頁(yè)腳的源碼,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2018-03-03
Python中等待5秒并暫停執(zhí)行的方法總結(jié)
Python 具有各種功能和庫(kù)來(lái)創(chuàng)建交互式應(yīng)用程序,用戶可以在其中提供輸入和響應(yīng), 我們可以創(chuàng)建需要暫停應(yīng)用程序執(zhí)行的情況,本文主要和大家分享三個(gè)Python 中等待 5 秒并暫停執(zhí)行的方法,有需要的可以參考下2023-10-10
Python實(shí)現(xiàn)強(qiáng)制復(fù)制粘貼的示例詳解
下個(gè)文檔還要馬內(nèi)?還好我會(huì)Python,本文就來(lái)教大家來(lái)一手如何利用Python實(shí)現(xiàn)強(qiáng)制復(fù)制粘貼。文中的示例代碼講解詳細(xì),感興趣的小伙伴可以了解一下2022-12-12

