все Python 3Итераторы и генераторыпонятие
itertools.groupby
itertools
Группирует последовательные одинаковые элементы. Данные должны быть отсортированы по ключу!
Синтаксис
from itertools import groupby
groupby(iterable, key=None)
Главная ловушка после «забыл отсортировать» — группа живёт только до перехода к следующей. Все группы делят один исходный итератор, поэтому list(groupby(data)) даёт пустые группы: пока вы дойдёте до конца, предыдущие уже съедены. Нужен весь результат сразу — забирайте list(group) внутри цикла, до следующей итерации.
Примеры
from itertools import groupby
data = ['A', 'A', 'B', 'B', 'B', 'A']
for key, group in groupby(data):
print(key, list(group)) # → A ['A', 'A'] / B ['B', 'B', 'B'] / A ['A']
# Группирует только соседей — для полной группировки сортируют заранее
from itertools import groupby
words = ['apple', 'apricot', 'banana', 'blueberry', 'cherry']
for letter, group in groupby(words, key=lambda w: w[0]):
print(letter, list(group)) # → a ['apple', 'apricot'] / b ['banana', 'blueberry'] / c ['cherry']
from itertools import groupby
data = sorted([1, 1, 2, 2, 2, 3])
print({k: list(v) for k, v in groupby(data)}) # → {1: [1, 1], 2: [2, 2, 2], 3: [3]}
nums = sorted([1, 2, 4, 6, 3, 7, 8], key=lambda x: x % 2)
for parity, grp in groupby(nums, key=lambda x: x % 2):
print('odd' if parity else 'even', list(grp)) # → even [2, 4, 6, 8] / odd [1, 3, 7]
# Длины серий
from itertools import groupby
runs = [(k, len(list(v))) for k, v in groupby('AAABBBCCDDDDEE')]
print(runs) # → [('A', 3), ('B', 3), ('C', 2), ('D', 4), ('E', 2)]
См. также
Открыть в полном глоссарииdocs.python.orgСообщить о неточности