Даны два отсортированных массива a , b типа T с размерами n и m . Я ищу алгоритм, который объединяет два массива в новый массив (максимальный размер n + m).
Если у вас дешевая операция сравнения, это довольно просто. Просто возьмите из массива с самым низким первым элементом, пока один или оба массива не пройдут полностью, затем добавьте остальные элементы. Примерно так /programming/5958169/how-to-merge-two-sorted-arrays-into-a-sorted-array
Однако ситуация меняется, когда сравнение двух элементов намного дороже, чем копирование элемента из исходного массива в целевой массив . Например, у вас может быть массив больших целых чисел произвольной точности или строки, где сравнение может быть довольно дорогим. Просто предположим, что создание массивов и копирование элементов бесплатное, и единственное, что стоит, - это сравнение элементов.
В этом случае вы хотите объединить два массива с минимальным количеством сравнений элементов . Вот несколько примеров, где вы должны быть в состоянии сделать намного лучше, чем простой алгоритм слияния:
a = [1,2,3,4, ... 1000]
b = [1001,1002,1003,1004, ... 2000]
Или
a = [1,2,3,4, ... 1000]
b = [0,100,200, ... 1000]
Есть несколько случаев, когда простой алгоритм слияния будет оптимальным, например,
a = [1,3,5,7,9,....,999]
b = [2,4,6,8,10,....,1000]
Таким образом, алгоритм должен в идеале грациозно ухудшаться и выполнять максимум n + m-1 сравнений в случае чередования массивов, или, по крайней мере, в худшем случае.
Одна вещь, которая должна хорошо работать для списков с большой разницей в размерах, - это использовать бинарный поиск для вставки элементов меньшего массива в больший массив. Но это не будет изящно ухудшаться, если оба списка имеют одинаковый размер и чередование.
Единственная вещь, доступная для элементов, - это (общая) функция упорядочения, поэтому любая схема, которая делает сравнение дешевле, невозможна.
Любые идеи?
Я придумал этот бит в Scala . Я считаю, что это оптимально с точки зрения количества сравнений, но я не могу это доказать. По крайней мере, это намного проще, чем то, что я нашел в литературе.
А с момента первоначальной публикации я написал в блоге сообщение о том, как это работает.