python3 суммирует элементы формы списка списков

У меня есть список списков

lst = [[0,1],[1,1],[3,1],[1,2],[1,3],[3,5]]

Я хочу суммировать вторые пункты списков для равных первых пунктов. Результат должен выглядеть так

lst = [[0,1],[1,6],[3,6]]

Я попробовал что-то вроде этого:

lst=[[0, 0.25], [1, 0.125], [2, 0.0625], [3, 0.0625], [1, 0.125], [2, 0.0625], [3, 0.03125], [4, 0.03125]]
for listitem in range(len(lst)):
    first=listitem[0]
    second = 0
    for obj in lst:
        if obj[0] == first:
            second += obj[1]
            lst.remove(obj)
    listitem[1] = second

4 ответа

Решение

Использование defaultdict

    from collections import defaultdict

    lst=[[0, 0.25], [1, 0.125], [2, 0.0625], [3, 0.0625], [1, 0.125], [2, 0.0625], [3, 0.03125], [4, 0.03125]]

    res = defaultdict(int)    
    for el in lst:
        res[el[0]] += el[1] 
    res_list = [[k,v] for (k,v) in res.items()]

    print(res_list)

[[0, 0.25], [1, 0.25], [2, 0.125], [3, 0.09375], [4, 0.03125]]

groupby возвращает ключ и итератор для элементов с одинаковым ключом. Должен быть передан список, отсортированный по тому же ключу:

from itertools import groupby
from operator import itemgetter

lst = [[0,1],[1,1],[3,1],[1,2],[1,3],[3,5]]

result = [[k,sum(b for a,b in g)]
           for k,g in groupby(sorted(lst),key=itemgetter(0))]

print(result)

Выход:

 [[0, 1], [1, 6], [3, 6]]

Еще один способ думать об этом заключается в том, что первым элементом в каждой паре является keyи второй value - так что если вы создаете dict затем вы можете добавлять значения вместе, когда вы сталкиваетесь с каждой клавишей - и это еще проще, если вы используете defaultdict:

from collections import defaultdict

summary = defaultdict(int)
for sublist in lst:
    key, value = sublist
    summary[key] += value

print(summary.items())

Линия summary[key] += value это рабочая лошадка здесь. Что оно делает:

  • смотрит вверх key В итоге
  • если его не существует, добавьте его и используйте int создать значение по умолчанию
  • вернуть значение (уже там или недавно созданный)
  • добавить новое значение к нему
  • сохранить его обратно summary под key

range(n) производит список, такой как [0,1,2...n-1]так что тип listitem является int скорее, чем list,

lst=[[0, 0.25], [1, 0.125], [2, 0.0625], [3, 0.0625], [1, 0.125], [2, 0.0625], [3, 0.03125], [4, 0.03125]]
for listitem in lst:
    first = listitem[0]
    second = 0
    for obj in lst:
        if obj[0] == first:
            second += obj[1]
            lst.remove(obj)
    listitem[1] = second        
Другие вопросы по тегам