设置只读属性
一:设置只读属性的方式:
class Person(object):
def __init__(self):
self.__age = 18
# @property 可以使用属性的方式来访问这个方法
@property
def age(self):
return self.__age
p = Person()
# 这样的实例属性进行赋值,相当于给这个实例加一个实例属性,并不是修改类里面的实例属性,因为双下划线是私有属性,不能读,不能写
p.__age = 999
print(p.__dict__) #
# 这样实例对象读取实例方法以读取实例属性一样
print(p.age) # 18
# 只读赋值,不能修改,这样就无法修改. AttributeError: can't set attribute
p.age = 888
二:property的设置,对私有属性操作
# property作用:
# 可以将一些属性的操作方法关联到某一个属性
"""
概念:
经典类:没有继承(object)
新式类: 继承(object)
python2版本定义一个类时,默认不继承(object)
python3版本定义一个类时,继承(object)
建议使用新式类
"""
# 查看当前的python版本是否继承(object)
class Person01:
pass
# 输出有object,表示是新式类,可以不用定义类后面写object,但是为了兼容python2版本,建议写object
print(Person01.__bases__) # (<class 'object'>,)
一.property使用方式1
class Person(object):
def __init__(self):
self.__age = 18
def get_age(self):
return self.__age
def set_age(self, value):
print("--set---")
self.__age = value
def del_age(self):
print("--del--")
del self.__age
# 通过property合并三种实例方法来实现对私有属性的读,写,删。
age = property(get_age, set_age, del_age)
# 创建一个实例对象,以访问实例方法的形式来访问实例属性,这样就可以像操作实例属性那样操作。
p = Person()
print(p.age)
# 通过实例方法的形式来修改实例私有属性,
p.age = 80
print(p.age)
print(p.__dict__)
#删除这个实例属性,
del p.age
print(p.__dict__)
# 方式1补充,方式1其实还是可以通过实例内置的属性可以修改,不叫真正的只读,叫伪只读属性
class Person(object):
def __init__(self):
self.__age = 18
# 通过property来设置实例方式的形式进行对属性的访问
@property
def age(self):
print("--get--")
return self.__age
p = Person()
print(p.age)
# 修改只读属性,失败
# p.age = 999 # AttributeError: can't set attribute
# 读取实例的所有属性,
print(p.__dict__) # {'_Person__age': 18}
#可以通过名转换来读取,_类名__age
print(p._Person__age)
# 修改只读属性
p._Person__age = 888
print(p.__dict__) # {'_Person__age': 888}
#property使用方式2
class Person(object):
"""
当我们通过实例.属性 = 值,给一个实例增加一个属性,或者说,修改一下属性值的时候,
都会调用方法,在这个方法内部,才会真正的把这个属性以及对应的数据存储到__dict__字典里面
"""
def __setattr__(self, key, value):
# 判定,key是否是我们要设置的只读属性名称,并且如果这个属性存在实例属性中,则只能读取,否则就增加
if key == "age" and key in self.__dict__.keys():
print("这个属性是只读属性,不能设置数据")
else:
self.__dict__[key] = value
#
p = Person()
# p.age : 当我们通过实例.属性 = 值就调用__setattr_——方法来读取实例属性,如果当前的age是存在实例属性字典里,就读取,否则就增加这个实例属性
p.age = 87
print(p.__dict__) # {'age': 87}
print(p.age) # 87
# 上面操作已经添加到这个实例属性了,修改这个只读属性修改不成功
p.age = 66 #调用__setattr_——方法, 返回: 这个属性是只读属性,不能设置数据返回
print(p.age) # 还是87
print(p.__dict__) # {'age': 87}