How to sum items within a list when some of those items are also lists?

Viewed 65

I'm trying to write a function which would sum the items in a list, including items which are lists themselves (or lists of lists...)

def sum_list_recursive(lst):
    sum = 0
    for i in range(len(lst)):
        if type(lst[i]) == "list":
            sum = sum + sum_list_recursive(lst[i])
        else:
            sum = sum + lst[i]
    return sum

Error:

returns: "*Traceback (most recent call last):
  File "C:/Users", line 13, in <module>
    sum_list_recursive([1,2,[3,4],[5,6]])
  File "C:/Users", line 10, in sum_list_recursive
    sum = sum + lst[i]
TypeError: unsupported operand type(s) for +: 'int' and 'list'*"

and I can't tell why or how to fix it.

Thanks in advance!

5 Answers
def sum_list_recursive (lst):
    return sum(sum_list_recursive(i) if isinstance(i, list) else i for i in lst)

my_list = [1, [2, [3, 4], 5, [6, 7, 8]], [9, 10]]
print (sum_list_recursive(my_list))
# --> 55

That’s probably the most concise and most “pythonic” way to solve this.

By the way, the actual error in your code snipped is that type() returns a type (i.e. a class), not a string. But in your if statement you compare it with the string "list", so the result is always False.

I would split this problem into two stages. In the first stage, the list is flattened and in the second one, the items are summed together.

Like so:

from collections.abc import Iterable

def flatten(l):
    for el in l:
        if isinstance(el, Iterable) and not isinstance(el, (str, bytes)):
            yield from flatten(el)
        else:
            yield el


l = [1, 2, [3, 4], [[5, 0], 6]]  # irregularly nested list of arbitrary depth

res = sum(flatten(l))
print(res)  # 21

Note that the flattening yields the elements one by one thus making this approach quite efficient.

The flatten function was written by @Cristian on another SO question.


Note that the code provided above does not offer protection for mixed data types and will brake if e.g., one of the lists contains a string as well. I will leave that for you to fix.

You need to deflatten the list first . Here is similar kind of query posted on stack overflow

from collections.abc import Iterable

def flatten(l):
    for el in l:
        if isinstance(el, Iterable) and not isinstance(el, (str, bytes)):
            yield from flatten(el)
        else:
            yield el

print(sum(flatten(list)))

You can try this simple code :

a = [1,2,3,4,[1,2,3,4]]

sum1  = 0 
for i in a :
    if type(i) == list:
        sum1  = sum1+sum(i)
    else:
        sum1 = sum1+i
 print(sum1)

or with recusrion

array = [1,2,3,4,[1,2,3,4]]

def productSum(array):
    
    sum1 = 0
    for i in array:
        if type(i) is list:
            sum1 += productSum(i)
        else:
            sum1 += i
    return sum1

print(productSum(array))
    
   
        

Maybe is not the most efficient but it's a fully recursive solution.

def recursive_sum( total, _list ):
    for element in _list:
        if isinstance( element, list ):
            recursive_sum( total, element )
        else:
            total[0]+=element
    return total

l = [1, 2, 3, [2, 5, 6], 5]
total = [0]
print(recursive_sum(total, l))
Related