I have a Serie class implemented to represent series of data and it's tag. When I add Serie objects and also numbers I get the expected output. However when I sum the same elements within a list I get following error message:
TypeError: unsupported operand type(s) for +: 'int' and 'Serie'
Toy example code
As a toy example code to understand the problem we can use:
import pandas as pd
import numpy as np
class Serie(object):
def __str__(self):
s = "> SERIE " + str(self.tag) + ": \n"
s += str(self.data)
return s
def __init__(self, tag=None, data=pd.DataFrame()):
"""
Creates object Serie
@type tag: str
@param tag: Tag for the Serie
"""
self.tag = tag
self.data = data
def __add__(self, other):
if isinstance(other, int) or isinstance(other, float):
tag = str(other) + "+" + self.tag
serie = Serie(tag)
serie.data = self.data + other
else:
try:
tag = self.tag + "+" + other.tag
except:
print ("ERROR: You can't add to somehing that is not a Serie or a number." )
return None
serie = Serie(tag)
serie.data = self.data + other.data
return serie
s1 = Serie("fibonacci",pd.Series([1,1,2,3,5,8]))
s2 = Serie("2power",pd.Series(np.linspace(1,6,6)**2))
s3 = 10
sumSerie = s1+s2+s3
print sumSerie
This prints the result as expected:
>>>
> SERIE 10+fibonacci+2power:
0 12.0
1 15.0
2 21.0
3 29.0
4 40.0
5 54.0
dtype: float64
Error when using sum of objects within list
However when I run following lines:
l = [s1,s2,s3]
sum(l)
I get error message:
sum(l) TypeError: unsupported operand type(s) for +: 'int' and 'Serie'
And same error message is displayed when I run:
l2 = [s1,s2]
sum(l2)
But in l2 list there is no int variable.
Questions
Why is this error message being displayed? This is confusing as I was able to sum the objects outside the list.
Is there something I can do in order to achieve performing the sum of the objects within the list?
EDIT
As suggested in the comments, I added the __radd__ to correctly overload the add method. So I added the below lines to the Serie class:
def __radd__(self,other):
return self.__add__(other)
Then the sum works. But not as expected.
If I run the below code:
>>> print sum(l)
I get this output:
> SERIE 10+0+fibonacci+2power:
0 12.0
1 15.0
2 21.0
3 29.0
4 40.0
5 54.0
dtype: float64
Which is definitely not the same I expected. There is a +0 extra within the tag. How can this be? However if I use the option I stated in my answer print np.array(l).sum() the result is correct.
EDIT 2
After overloading add method correctly I was suggested to use below method to perform the sum as expected:
reduce(lambda a, b: a+b, l)
This approach worked to be able to use sum function for the list and get the correct result.
As stated by pault in the comments in sum method "start defaults to 0" as detailed in sum function's documentation. That was why the extra +0 was being added to the tag before.
In conclusion I believe I would preferrably use the option using numpy.sum function instead:
np.array(l).sum()