2013-10-10 29 views
2
class C(object): 
    def __init__(self, value): 
    self.value = value 

    def __add__(self, other): 
    if isinstance(other, C): 
     return self.value + other.value 
    if isinstance(other, Number): 
     return self.value + other 
    raise Exception("error") 


c = C(123) 

print c + c 

print c + 2 

print 2 + c 

顯然,前兩個打印語句將工作,第三個失敗,因爲int。 add()不能處理一個C類實例。如何獲得__add__調用

246 
125 
    print 2 + c 
TypeError: unsupported operand type(s) for +: 'int' and 'C' 

有沒有辦法來解決這個問題,所以2 + C會導致C. 添加()被調用?

回答

4

您需要添加__radd__以及處理相反的情況:

def __radd__(self, other): 
    if isinstance(other, C): 
     return other.value + self.value 
    if isinstance(other, Number): 
     return other + self.value 
    return NotImplemented 

,並請注意您應該不提例外;改爲返回NotImplemented單身人士。這樣其他對象仍然可以嘗試支持__add____radd__爲您的對象,並將有機會實現添加。

當您嘗試添加兩種類型ab時,Python首先嚐試呼叫a.__add__(b);如果該呼叫返回NotImplemented,則嘗試使用b.__radd__(a)

演示:

>>> from numbers import Number 
>>> class C(object): 
...  def __init__(self, value): 
...   self.value = value 
...  def __add__(self, other): 
...   print '__add__ called' 
...   if isinstance(other, C): 
...    return self.value + other.value 
...   if isinstance(other, Number): 
...    return self.value + other 
...   return NotImplemented 
...  def __radd__(self, other): 
...   print '__radd__ called' 
...   if isinstance(other, C): 
...    return other.value + self.value 
...   if isinstance(other, Number): 
...    return other + self.value 
...   return NotImplemented 
... 
>>> c = C(123) 
>>> c + c 
__add__ called 
246 
>>> c + 2 
__add__ called 
125 
>>> 2 .__add__(c) 
NotImplemented 
>>> 2 + c 
__radd__ called 
125 
2

您需要在課上實施__radd__

def __radd__(self, other): 
    return self.value + other 

這會導致自動調用,因爲int類將引發NotImplemented錯誤