Python中的property是一种特殊的装饰器,它可以将函数转换为属性,即方法调用像属性一样使用。在Python中,属性和特性是一对密切相关的概念,因为它们共同构成了一个类的接口。
假设现在有一个名为Person的类,有属性name和age,我们需要对属性进行一些限制。下面是使用property实现对属性访问的过程:
class Person:
def __init__(self, name, age):
self._name = name
self._age = age
@property
def name(self):
return self._name
@property
def age(self):
return self._age
@age.setter
def age(self, value):
if not isinstance(value, int):
raise ValueError("age must be an integer")
if value <= 0 or value > 120:
raise ValueError("age must between 1 and 120")
self._age = value
p = Person("Bob", 20)
print(p.name) # output: Bob
print(p.age) # output: 20
p.age = 25 # set age
print(p.age) # output: 25
在上面的示例中,我们通过@property将name和age方法转换为属性。对于getter方法,我们直接使用@property进行装饰;对于setter方法,我们需要使用@xxx.setter装饰器,其中xxx表示属性名。
除了基本用法之外,property还有一些高级用法,比如可以使用property实现只读属性,如果尝试设置只读属性,就会引发AttributeError异常。示例代码如下所示:
class Person:
def __init__(self, name):
self._name = name
@property
def name(self):
return self._name
@property
def age(self):
raise AttributeError("age is a read-only attribute")
p = Person("Bob")
print(p.name) # output: Bob
print(p.age) # output: AttributeError
p.age = 25 # set age, AttributeError
Python中的属性和特性之间存在着优先权,即如果类中既有属性又有特性,那么Python会根据以下规则来决定调用哪个:
以下是示例代码,用来说明属性和特性之间的优先权:
class DemoClass:
def __init__(self):
self._value = 1
@property
def value(self):
print("get value")
return self._value
@value.setter
def value(self, v):
print("set value=%s" % v)
self._value = v
def __getattr__(self, name):
print("__getattr__ %s" % name)
return "not found"
def __getattribute__(self, name):
print("__getattribute__ %s" % name)
return object.__getattribute__(self, name)
d = DemoClass()
print(d.value) # output: __getattribute__ value\nget value\n1
print(d.__dict__) # output: {'_value': 1}
d.value = 2 # output: __getattribute__ value\nset value=2
print(d.__dict__) # output: {'_value': 2}
print(d.x) # output: __getattribute__ x\n__getattr__ x\nnot found
从上面的示例可以看出,通过属性访问特性时,特性具有更高的优先权。此外,如果属性和特性的名字相同,则属性拥有更高的优先权。如果属性和特性都不存在,那么Python将调用对象的__getattr__方法。此外,属性和方法的优先级同样存在关系,如果属性和方法的名字相同,那么属性拥有更高的优先级。
本文链接:http://task.lmcjl.com/news/14730.html