Merge Sort
September 14, 2024·Johnathan Jacobs
An efficient, general purpose, comparison-based Divide and Conquer sorting algorithm.
Algorithm
Divide the unsorted list into $n$ sublists, each containing one element. A list of one element is considered sorted.
Repeatedly merge sublists to produce new sorted sublists, until only one list remains.
Top-down implementation
This implementation is $O(nlogn)$ as every iteration on $n$ causes work on half as much $n$.
std::vector<int> TopDownMergeSort(std::vector<int> input) {
auto work = input;
TopDownSplitMerge(input, 0, input.size(), work);
return input;
}
void TopDownSplitMerge(std::vector<int>& in, std::size_t begin, std::size_t end, std::vector<int>& wrk) {
if(end - beging <= 1) return;
std::size_t mid = (end + begin) / 2;
// split the input in two
TopDownSplitMerge(wrk, begin, mid, in); // sort the left run
TopDownSplitMerge(wrk, mid, end, in); // sort the right run
// merge the runs back
TopDownMerge(in, begin, mid, end, wrk);
}
void TopDownMerge(std::vector<int>& in, std::size_t beg, std::size_t mid, std::size_t end, std::vector<int>& wrk) {
std::size_t i = beg;
std::size_t j = mid;
// for each output element, choose either the left or the right input in order
for (auto k = beg; k < end; ++k) {
if (i < mid && (j >= end || wrk[i] <= wrk[j])) {
in[k] = wrk[i];
++i;
} else {
in[k] = wrk[j];
++j;
}
}
}
List-Based Implementation
More efficient than array-based as we can just swap pointers. Though, think of the cache misses!