2012-02-06 15 views
8

Estoy un poco confundido acerca de las propiedades en python. Considere el siguiente códigopython property getter/setter confusion

class A: 
    @property 
    def N(self): 
     print("A getter") 
     return self._N 
    @N.setter 
    def N(self,v): 
     print("A setter") 
     self._N = v 

    def __init__(self): 
     self._N = 1 

class B: 
    @property 
    def N(self): 
     print("B getter") 
     return self.a.N 
    @N.setter 
    def N(self,v): 
     print("B setter") 
     self.a.N = v 

    def __init__(self): 
     self.a = A() 

if __name__ == '__main__': 
    b=B() 
    b.N = 2 
    print(b.N, b.a.N) 
    b.N = 3 
    print(b.N, b.a.N) 

B debería ser algo así como un envoltorio para A. Se utiliza captadores y definidores para mapear las propiedades de un sobre sí misma (por supuesto también se podría hacerlo a través de la herencia). El problema es que simplemente no funciona como se esperaba en python2.6 mientras lo hace en python3:

> python2 test.py 
A getter 
(2, 1) 
A getter 
(3, 1) 

> python3 test.py 
B setter 
A setter 
B getter 
A getter 
A getter 
2 2 
B setter 
A setter 
B getter 
A getter 
A getter 
3 3 

¿Estoy haciendo algo mal o dónde exactamente es el problema?

Respuesta

18

A y B deben ser clases de nuevo estilo en Python 2.x.

property([fget[, fset[, fdel[, doc]]]])

devolver un atributo de propiedad de new-style classes (clases que se derivan de object).

Así que si usted se derivan de object

class A(object): 
    ... 

class B(object): 
    ... 

Su código funciona como se esperaba.

+0

bien, tienes razón, eso lo resuelve, pero de todos modos no entiendo qué está mal aquí. – buergi

+1

@buergi Las clases de estilo antiguo no pueden tener descriptores. '@ property' es un descriptor. Más información en [Referencia del modelo de Python Data] (http://docs.python.org/reference/datamodel.html) – reclosedev