Выберите пары чисел с минимальной общей разницей

дано n пары чисел, выберите k пары так, чтобы разность между минимальным значением и максимальным значением минимальна. Обратите внимание, что 2 числа в 1 паре не могут быть разделены. Пример (n=5, k=3):

INPUT        OUTPUT (return the index of the pairs)
5 4          1 2 4
1 5
9 8
1 0
2 7

в этом случае выберите (5,4) (1,5) (1,0) даст разницу в 5 (макс-5, мин 0). Я ищу эффективный способ (N log n) делать это, так как вход будет будьте довольно большими, и я не хочу проходить через все возможные случаи.

спасибо.

Примечание: код не требуется. Объяснения решения достаточно.

2 ответов


вот метод с O(n log n) задачи:

сначала отсортируйте массив в соответствии с меньшим числом в паре. Теперь вернитесь от последнего элемента в отсортированном массиве (пара с самым высоким минимумом).

по мере того как мы идем назад, элементы уже посещенные обязательно будут иметь равный или более высокий минимум чем текущий элемент. Магазин посещенных пар в макс кучи по maximal номер в посещаемой паре. Если размер кучи меньше k-1, продолжайте добавлять в кучу.

как только размер кучи равен k-1, начните запись и сравнение лучшего интервала до сих пор. Если размер кучи превышает k-1, pop максимальный элемент выкл. Куча гарантированно содержит первое k-1 пары, где минимальное число больше или равно текущему минимальному числу, а максимальное наименьшее (так как мы продолжаем выскакивать максимальный элемент, когда размер кучи превышает k-1).

Общее время O(n log n) для сортировки + O(n log n) для прохода и поддержания кучи = O(n log n) в общей сложности.

пример:

5 4
1 5
9 8
1 0
2 7

k = 3

Sort pairs by the smaller number in each pair:
[(1,0),(1,5),(2,7),(5,4),(9,8)]

Iterate from end to start:
i = 4; Insert (9,8) into heap
i = 3; Insert (5,4) into heap
i = 2; Range = 2-9
i = 1; Pop (9,8) from heap; Range = 1-7
i = 0; Pop (2,7) from heap; Range = 0-5

Minimal interval [0,5] (find k matching indices in O(n) time)

позволяет сохранить отсортированные массивы: один, который сортируется по минимальному числу в паре, а другой-по максимальному. Позволяет перебирать первый массив и фиксировать минимальное число в ответе. Мы можем сохранить указатель на k-е число во втором массиве. Когда мы переходим к следующей паре, мы удаляем все пары с меньшим минимальным значением из второго массива и указателя вперед, если это необходимо. Найти позицию в log n время во втором массиве мы можем сохранить дополнительную карту между парой и положением.