|
| 1 | +/** |
| 2 | + * Created by Liam Huang (Liam0205) on 2018/10/17. |
| 3 | + */ |
| 4 | + |
| 5 | +#ifndef SORTS_MERGE_SORT_HPP_ |
| 6 | +#define SORTS_MERGE_SORT_HPP_ |
| 7 | + |
| 8 | +#include <functional> |
| 9 | +#include <algorithm> |
| 10 | +#include <iterator> |
| 11 | +#include <vector> |
| 12 | + |
| 13 | +namespace detail { |
| 14 | +template <typename InputIt1, typename InputIt2, typename OutputIt, |
| 15 | + typename BinaryPred = std::less<typename std::iterator_traits<InputIt1>::value_type>> |
| 16 | +OutputIt merge(InputIt1 first1, InputIt1 last1, |
| 17 | + InputIt2 first2, InputIt2 last2, |
| 18 | + OutputIt d_first, |
| 19 | + BinaryPred comp = BinaryPred()) { |
| 20 | + for (; first1 != last1; ++d_first) { |
| 21 | + if (first2 == last2) { |
| 22 | + return std::copy(first1, last1, d_first); |
| 23 | + } |
| 24 | + if (comp(*first2, *first1)) { |
| 25 | + *d_first = *first2; |
| 26 | + ++first2; |
| 27 | + } else { |
| 28 | + *d_first = *first1; |
| 29 | + ++first1; |
| 30 | + } |
| 31 | + } |
| 32 | + return std::copy(first2, last2, d_first); |
| 33 | +} |
| 34 | +} // namespace detail |
| 35 | + |
| 36 | +template <typename FrwdIt, |
| 37 | + typename BinaryPred = std::less<typename std::iterator_traits<FrwdIt>::value_type>> |
| 38 | +void merge_sort(FrwdIt first, FrwdIt last, BinaryPred comp = BinaryPred()) { |
| 39 | + const auto len = std::distance(first, last); |
| 40 | + if (len <= 1) { return; } |
| 41 | + auto cut = first + len / 2; |
| 42 | + merge_sort(first, cut, comp); |
| 43 | + merge_sort(cut, last, comp); |
| 44 | + std::vector<typename std::iterator_traits<FrwdIt>::value_type> tmp; |
| 45 | + tmp.reserve(len); |
| 46 | + detail::merge(first, cut, cut, last, std::back_inserter(tmp), comp); |
| 47 | + std::copy(tmp.begin(), tmp.end(), first); |
| 48 | +} |
| 49 | + |
| 50 | +#endif // SORTS_MERGE_SORT_HPP_ |
| 51 | + |
0 commit comments