San9096
San9096

Reputation: 251

Summing elements of list of lists in Python

I have the following list of lists:

myList = [[8100, 3], [8200, 5], [8400, 8]]

I would like to sum the second element of every sub-list to the next second element of the next list and so on.

Here is how it should look:

myList = [[8100, 3], [8200, 5], [8400, 8]]
myNewList = [[8100, 3], [8200, 8], [8400, 16]]

Because 3+5=8, 8+8=16 and so on. Is there any method to do this? Or am i supposed to write my own function for that, using NumPy for example?

Upvotes: 0

Views: 2061

Answers (7)

Brayoni
Brayoni

Reputation: 766

You can achieve the results in one pass O(n) and without allocating any additional space O(1), unless you want to, by looping from the first element, progressively updating the items to be summed as follows:

In [1]: A = [[8100, 3], [8200, 5], [8400, 8]]

In [2]: for i in range(1, len(A)):
            A[i][-1] += A[i-1][-1]

In [3]: A
Out[3]: [[8100, 3], [8200, 8], [8400, 16]]

Upvotes: 2

dawg
dawg

Reputation: 104092

You can use the new assignment operator (or walrus operator) to create an accumulator inside a comprehension:

myList = [[8100, 3], [8200, 5], [8400, 8]]

acc=0
new_list=[[sl1, acc := acc + sl2] for sl1, sl2 in myList]
>>> new_list
[[8100, 3], [8200, 8], [8400, 16]]

This is only for Python 3.8+

Upvotes: 1

Zain Arshad
Zain Arshad

Reputation: 1907

A very simple way to solve this, is to maintain a total variable and replace the second value of each sub-list with this sum.

myList = [[8100, 3], [8200, 5], [8400, 8]]
total, new_list = 0, []

for sublist in myList:
    total += sublist[1]
    new_list.append([sublist[0],total])

print(new_list)

Output

[[8100, 3], [8200, 8], [8400, 16]]

Upvotes: 1

Błotosmętek
Błotosmętek

Reputation: 12927

col1, col2 = zip(*myList)
# col1 == (8100, 8200, 8400), col2 == (3, 5, 8)
sums = [ sum(col2[:i]) for i, _ in enumerate(col2, 1) ]
# sums == [3, 8, 16]
myNewList = [ list(x) for x in zip(col1, sums) ]
# myNewList == [[8100, 3], [8200, 8], [8400, 16]]

Upvotes: 1

Cromo
Cromo

Reputation: 199

I made an example for you as clear as possible: you can make the function drier and more efficient, if you think about merging the loops.

L = [[8100, 3], [8200, 5], [8400, 8]]

def newList(L):
    gen = []
    for subL in L:
        if len(gen) > 0:
            gen.append(gen[-1] + subL[1])
        else:
            gen.append(subL[1])

    for idx, subL in enumerate(L):
        subL[1] = gen[idx]

    print(L)

newList(L)

Output:

[[8100, 3], [8200, 8], [8400, 16]]

Upvotes: 0

Job
Job

Reputation: 26

this method should work:

myNewList = []
value = 0
for sublist in myList:
    value = sublist[1]+value
    newSublist = [sublist[0],value]
    myNewList.append(newSublist) 

so simply store the previous value in a temprary variable adn add that to the next sublists second element.

Upvotes: 1

Vishnudev Krishnadas
Vishnudev Krishnadas

Reputation: 10970

Use np.cumsum given your array is large or you wanna do further manipulations. For smaller ones custom python function would be better.

a = np.array(myList)
a[:, 1] = a[:, 1].cumsum()

Output

array([[8100,    3],
       [8200,    8],
       [8400,   16]])

Upvotes: 2

Related Questions