2010-11-15 10 views
52

Estoy tratando de utilizar las propiedades de estilo nueva declaración:'No se puede establecer el atributo' con propiedades de estilo nuevo en Python

class C(object): 
    def __init__(self): 
     self._x = 0 

    @property 
    def x(self): 
     print 'getting' 
     return self._x 

    @x.setter 
    def set_x(self, value): 
     print 'setting' 
     self._x = value 

if __name__ == '__main__': 
    c = C() 
    print c.x 
    c.x = 10 
    print c.x 

y ver lo siguiente en la consola:

pydev debugger: starting 
getting 
0 
File "\test.py", line 55, in <module> 
c.x = 10 
AttributeError: can't set attribute 

¿Qué estoy haciendo mal? P.S .: La declaración de estilo antiguo funciona bien.

+0

He retrocedido la edición que convierte ''setting'' (a docstring) en configuración' print'' (una declaración simple de depuración). Si bien es ciertamente plausible que la declaración impresa fue intencionada, no hay daño o error en la documentación, y no afecta la pregunta en absoluto. –

Respuesta

76

The documentation says the following sobre el uso de la forma decorador de property: (. X en este caso)

Asegúrese de darle a las funciones adicionales del mismo nombre que la propiedad original

tengo no tengo idea de por qué es así ya que si usas property como función para devolver un atributo, los métodos se pueden llamar como quieras.

Así que hay que cambiar el código a la siguiente:

@x.setter 
def x(self, value): 
    'setting' 
    self._x = value 
+0

Ah, genial, vi esto en otro lugar, pero supuse que podrían ignorar la falta de sobrecarga de métodos de Python. Esto en realidad se ve más limpio que un nombre 'set_x'! :) – Darthfett

+0

¿Para qué sirve la cadena 'setting'? – zakdances

+1

@yourfriendzak - Es un docstring http://www.python.org/dev/peps/pep-0257/ –

13

El método setter debe tener el mismo nombre que el getter. No te preocupes, el decorador sabe cómo diferenciarlos.

@x.setter 
def x(self, value): 
... 
6

Cuando se llama @ x.setter, x.getter @ o @ x.deleter, se está creando un nuevo objeto de propiedad y dándole el nombre de la función que está decorando. Entonces, realmente, todo lo que importa es que la última vez que usó un decorador @ x. * Er en la definición de la clase, tiene el nombre que realmente quiere usar. Pero dado que esto dejaría el espacio de nombres de su clase contaminado con versiones incompletas de la propiedad que desea usar, es mejor usar el mismo nombre para limpiarlas.

Cuestiones relacionadas