2010-02-15 10 views
7

Soy nuevo en Python así que me disculpo de antemano si esta es una pregunta estúpida.sobrecarga asignaciones aritméticas aumentadas en python

Para una tarea, necesito sobrecargar asignaciones aritméticas aumentadas (+ =, - =,/=, * =, ** =,% =) para una clase myInt. Revisé la documentación de Python y esto es lo que ocurrió:

def __iadd__(self, other): 

    if isinstance(other, myInt): 
     self.a += other.a 
    elif type(other) == int: 
     self.a += other 
    else: 
     raise Exception("invalid argument") 

self.a y other.a refiero a la int almacenado en cada instancia de clase. He intentado probar esta de la siguiente manera, pero cada vez que llego 'Ninguno' en lugar del valor esperado 5:

c = myInt(2) 
b = myInt(3) 
c += b 
print c 

puede alguien decirme por qué ocurre esto? Gracias por adelantado.

+2

Creo que no hay preguntas estúpidas .. –

Respuesta

14

Debe agregar return self a su método. Explicación:

La semántica de a += b, cuando type(a) tiene un método especial __iadd__, se define como:

a = a.__iadd__(b) 

así que si __iadd__ vuelve algo diferente a self, eso es lo que va a ser obligado a nombrar a después de la operación. Al perder una declaración return, el método que publicó es equivalente a uno con return None.

+1

Alex, siempre me encantan tus respuestas! –

+0

@Srinivas, gracias! –

+0

¡Gracias por la explicación clara! – Mel

1

Sí, es necesario "auto retorno", que se verá así:

def __iadd__(self, other): 
    if isinstance(other, myInt): 
     self.a += other.a 
     return self 
    elif type(other) == int: 
     self.a += other 
     return self 
    else: 
     raise Exception("invalid argument") 
+2

Además, debe hacer que su 'Exception' sea' TypeError'. – jcdyer

7

operadores Aumentada en Python tienen que devolver el valor final que será asignado al nombre que están llamados, por lo general (y en su caso) self. Como todos los métodos de Python, perder una declaración de devolución implica devolver None.

Además,

  • Nunca jamás elevar Exception, que es imposible de alcanzar con cordura. El código para hacerlo tendría que decir except Exception, que capturará todas las excepciones. En este caso, quiere ValueError o TypeError.
  • No compruebe con type(foo) == SomeType. En este (y prácticamente todos) los casos, isinstance funciona mejor o al menos lo mismo.
  • Cada vez que haga su propio tipo, como myInt, debe nombrarlo con letras mayúsculas para que las personas puedan reconocerlo como un nombre de clase.
Cuestiones relacionadas