Puede leer más sobre ambos desde here. Pero aquí hay un ejemplo simple del mismo libro que trata de explicar la diferencia al resolver lo que esencialmente es el mismo problema. Como puede ver, la implementación que usa propiedades es mucho más simple.
Existen varias formas de acceder a los mecanismos internos de Python para obtener y establecer valores de atributos. La técnica más accesible es usar la función de propiedad para definir los métodos get, set y delete asociados con un nombre de atributo. La función de propiedad crea descriptores para usted. Una técnica ligeramente menos accesible, pero más extensible y reutilizable es definir usted mismo las clases de descriptores. Esto le permite una flexibilidad considerable. Para ello, cree una clase que defina los métodos get, set y delete, y asocie su clase de descriptor con un nombre de atributo.
La función de propiedad nos proporciona una forma práctica de implementar un descriptor simple sin definir una clase separada. En lugar de crear una definición de clase completa, podemos escribir las funciones del método getter y setter, y luego unir estas funciones a un nombre de atributo. ejemplo
descriptor:
ejemplo
class Celsius(object):
def __init__(self, value=0.0):
self.value= float(value)
def __get__(self, instance, owner):
return self.value
def __set__(self, instance, value):
self.value= float(value)
class Farenheit(object):
def __get__(self, instance, owner):
return instance.celsius * 9/5 + 32
def __set__(self, instance, value):
instance.celsius= (float(value)-32) * 5/9
class Temperature(object):
celsius= Celsius()
farenheit= Farenheit()
>>>
oven= Temperature()
>>>
oven.farenheit= 450
>>>
oven.celsius
232.22222222222223
>>>
oven.celsius= 175
>>>
oven.farenheit
347.0
propiedad:
class Temperature(object):
def fget(self):
return self.celsius * 9/5 + 32
def fset(self, value):
self.celsius= (float(value)-32) * 5/9
farenheit= property(fget, fset)
def cset(self, value):
self.cTemp= float(value)
def cget(self):
return self.cTemp
celsius= property(cget, cset, doc="Celsius temperature")
>>>
oven= Temperature()
>>>
oven.farenheit= 450
>>>
oven.celsius
232.22222222222223
>>>
oven.celsius= 175
>>>
oven.farenheit
347.0
Puede valer la pena señalar que pitón desalienta el uso de captadores y definidores excepto cuando sea necesario ... o puede que no .. –
@JoranBeasley No está tan desanimado como completamente innecesario. Como Python le permite anular el acceso a los atributos, puede decidir si necesita esto en una subclase. Si necesita una propiedad calculada, es apropiado usar un getter. En Java/C#, debe decidir por adelantado si desea permitir anular el acceso a un atributo específico y proporcionarlo en la parte superior de la jerarquía de clases. Es por eso que es común usar propiedades de forma generalizada: se hace "por las dudas". – millimoose