Вот версия на python (версии 2 и 3):
def aggregate(data):
data.sort()
i = 0
while i < len(data) - 1:
while i < len(data) - 1 and data[i][1] >= data[i+1][0]:
data[i] = (data[i][0], max(data[i][1], data[i+1][1]))
data.pop(i+1)
i += 1
if __name__ == '__main__':
itervals = [(1,2), (5,7), (9,12), (3,4), (5,6), (13,17)]
formatted = lambda vals: '[{}]'.format(', '.join('({}-{})'.format(
iterval[0], iterval[1])
for iterval in sorted(vals)))
print(formatted(itervals))
aggregate(itervals)
print(formatted(itervals))
Вывод:
[(1-2), (3-4), (5-6), (5-7), (9-12), (13-17)]
[(1-2), (3-4), (5-7), (9-12), (13-17)]
Примечание: это мутирует список кортежей на месте.Немного более общий, который будет работать со списком итераций, можно сделать, изменив строку:
data[i] = type(data[i])((data[i][0], max(data[i][1], data[i+1][1])))
В качестве альтернативы, если вы знаете, что у вас есть список изменяемых итераций, вы можете использовать:
data[i][1] = max(data[i][1], data[i+1][1])
Альтернативная версия, за которой может быть немного легче следовать, это:
def aggregate(data):
if not data:
return data
inputs = sorted(data)
result = [inputs[0]]
for next0, next1 in inputs[1:]:
last0, last1 = result[-1]
if next0 <= last1:
result[-1][1] = max(next1, last1)
else:
result.append([next0, next1])
return result
Обратите внимание, что эта версия предназначена для списка списков.