十四、python 訪問屬性和屬性裝飾器
訪問屬性:
1、直接訪問(上一講得直接操作)
2、通過自定義get() 、 set()方法來訪問
3、通過屬性裝飾器
@property 讀
@***.setter 寫
@***.deleter 刪除
4、通過屬性符訪問
代碼重用
描述符屬性必須定義爲類屬性
-----------------------------------------------------------
#屬性訪問
class Chinese(object):
nation = 'Chain'
def __init__(self, id, name):
self._id = id
self.__name = name
self.__mail = None
def sayHi(self, msg):
print self.__name,msg
#自定義get 、 set 方法訪問
def getId(self):
return self._id
def setId(self, id):
self._id = id
# 定義屬性裝飾器
@property
def name(self):
return self.__name
@name.setter
def name(self, name):
self.__name = name
@name.deleter
def name(self):
del self.__name
#定義實例
aidon = Chinese(1,'aidon')
print aidon.getId()
aidon.setId(10)
print aidon.getId()
print aidon.name
aidon.name = 'bajie'
print aidon.name
del aidon.name #刪除
#print aidon.name
print aidon._Chinese__mail
print aidon.__dict__
--------------------------------------------------------------
---------------------------------------------------------------
#類描述符定義
class Property(object):
def __init__(self, propname, datatype, default=None):
self._name = '_'+propname+'_'
self._type = datatype
self._default = default if default else self._type()
def __get__(self, instance, owner):
return getattr(instance,self._name,self._default)
def __set__(self, instance, value):
if not isinstance(value,self._type):
raise TypeError('Type Error,must be %s type0' % self._type)
setattr(instance,self._name,value)
def __del__(self):
pass
class Email(Property):
def __init__(self,propname,default=None):
super(Email,self).__init__(propname,str,default)
def __set__(self, instance, value):
if not isinstance(value,self._type):
raise TypeError('Type Error,must be %s type0' % self._type)
if not '@' in value:
raise ValueError('Email address is not valid')
setattr(instance,self._name,value)
class Chinese(object):
Id = Property('id', int) #描述符必須是類屬性,Id隨便定義,和後面沒有任何關係,它相當於對外訪問提供的一個接口
Name = Property('name', str)
Email = Email('email')
#注意:類的成員方法中,也必須使用類的描述符
def __init__(self,id,name,email):
self.Id = id
self.Name = name
self.Email = email
#---------使用交互式測試--------------------
aidon = Chinese()
aidon.__dict__
aidon.Id #此時都是默認類型的默認值纔對
aidon.Name
aidon.Email
#賦值
aidon.Id= 100
aidon.Name = 'aidon'
aidon.Email = '[email protected]'
aidon.Id
aidon.__dict__
#設置和類型不匹配的值
aidon.Name = 123123
aidon.Email = 'abc'
#測試類的成員方法
bajie = Chinese(1,'bajie','[email protected]')
bajie.Name
bajie.__dict__
-----------------------------------------------------------------