Namespaces
Variants

std::inplace_merge

От ru.cppreference.net
 
 
Библиотека алгоритмов
Ограниченные алгоритмы и алгоритмы для диапазонов (C++20)
Ограниченные алгоритмы, например ranges::copy, ranges::sort, ...
Немодифицирующие операции последовательностей    
Пакетные операции
(C++17)
Поисковые операции
Модифицирующие операции последовательностей
Операции копирования
(C++11)
(C++11)
Операции обмена
Операции преобразования
Операции генерации
Операции удаления
Операции изменения порядка
(до C++17)(C++11)
(C++20)(C++20)
Операции выборки
(C++17)

Сортировка и связанные операции
Операции разделения
(C++11)    

Операции сортировки
Операции двоичного поиска
(на разделённых диапазонах)
Операции над множествами (на отсортированных диапазонах)
Операции слияния (на отсортированных диапазонах)
Операции с кучей
Операции минимума/максимума
(C++11)
(C++17)
Операции лексикографического сравнения
Операции перестановок


Политики выполнения (C++17)
(только для демонстрации*)(C++26)

Численные операции
(C++11)
(C++17)
(C++17)    

Специализированные <memory> алгоритмы

Специализированные <random> алгоритмы
Библиотека C









 
Определён в заголовке <algorithm>
template< class BidirIt >
void inplace_merge( BidirIt first, BidirIt middle, BidirIt last );
(1) (constexpr начиная с C++26)
template< class ExecutionPolicy, class BidirIt >
void inplace_merge( ExecutionPolicy&& policy,
                    BidirIt first, BidirIt middle, BidirIt last );
(2) (начиная с C++17)
template< class BidirIt, class Compare >
void inplace_merge( BidirIt first, BidirIt middle, BidirIt last,
                    Compare comp );
(3) (constexpr начиная с C++26)
template< class ExecutionPolicy, class BidirIt, class Compare >
void inplace_merge( ExecutionPolicy&& policy,
                    BidirIt first, BidirIt middle, BidirIt last,
                    Compare comp );
(4) (начиная с C++17)

Объединяет два последовательных отсортированных диапазона [first, middle) и [middle, last) в один отсортированный диапазон [first, last).

1) Если [first, middle) или [middle, last) не является отсортированным относительно operator<(до C++20)std::less{}(начиная с C++20), поведение не определено.
3) Если [first, middle) или [middle, last) не отсортирован относительно comp, поведение не определено.
2,4) То же, что и (1,3), но выполняется в соответствии с policy.
Эти перегрузки участвуют в разрешении перегрузки только если значение следующего выражения равно true:

std::is_execution_policy_v<std::decay_t<ExecutionPolicy>>

(до C++20)

std::is_execution_policy_v<std::remove_cvref_t<ExecutionPolicy>>

(начиная с C++20)

Эта функция слияния является устойчивой, что означает, что для эквивалентных элементов в исходных двух диапазонах элементы из первого диапазона (с сохранением их исходного порядка) предшествуют элементам из второго диапазона (с сохранением их исходного порядка).

Если выполняется любое из следующих условий, поведение не определено:

  • Тип *first не является Swappable.
(до C++11)
(начиная с C++11)

Параметры

first - начало первого отсортированного диапазона
middle - конец первого отсортированного диапазона и начало второго
last - конец второго отсортированного диапазона
policy - политика выполнения для использования
comp - объект функции сравнения (т.е. объект, удовлетворяющий требованиям Compare), который возвращает ​true если первый аргумент меньше чем (т.е. упорядочен перед) второго.

Сигнатура функции сравнения должна быть эквивалентна следующей:

bool cmp(const Type1& a, const Type2& b);

Хотя сигнатура не обязана содержать const&, функция не должна изменять переданные ей объекты и должна быть способна принимать все значения типа (возможно const) Type1 и Type2 независимо от категории значения (таким образом, Type1& не разрешено, как и Type1 если только для Type1 перемещение не эквивалентно копированию(начиная с C++11)).
Типы Type1 и Type2 должны быть такими, чтобы объект типа BidirIt можно было разыменовать и затем неявно преобразовать в оба из них. ​

Требования к типам
-
BidirIt должен удовлетворять требованиям LegacyBidirectionalIterator.
-
Compare должен удовлетворять требованиям Compare.

Сложность

Пусть N равно std::distance(first, last):

1) Ровно N-1 сравнений с использованием operator<(до C++20)std::less{}(начиная с C++20) если доступно достаточно дополнительной памяти, иначе O(N⋅log(N)) сравнений.
2) O(N⋅log(N)) сравнений с использованием operator<(до C++20)std::less{}(начиная с C++20).
3) Ровно N-1 применений функции сравнения comp если доступно достаточно дополнительной памяти, иначе O(N⋅log(N)) применений.
4) O(N⋅log(N)) применений функции сравнения comp.

Исключения

Перегрузки с параметром шаблона с именем ExecutionPolicy сообщают об ошибках следующим образом:

  • Если выполнение функции, вызванной в рамках алгоритма, генерирует исключение и ExecutionPolicy является одной из стандартных политик, вызывается std::terminate. Для любой другой ExecutionPolicy поведение определяется реализацией.
  • Если алгоритму не удаётся выделить память, генерируется std::bad_alloc.

Возможная реализация

Смотрите реализации в libstdc++ и libc++.

Примечания

Эта функция пытается выделить временный буфер. Если выделение не удаётся, выбирается менее эффективный алгоритм.

Макрос проверки возможностей Значение Std Возможность
__cpp_lib_constexpr_algorithms 202306L (C++26) constexpr inplace merging (1), (3)

Пример

Следующий код является реализацией сортировки слиянием.

#include <algorithm>
#include <iostream>
#include <vector>

template<class Iter>
void merge_sort(Iter first, Iter last)
{
    if (last - first > 1)
    {
        Iter middle = first + (last - first) / 2;
        merge_sort(first, middle);
        merge_sort(middle, last);
        std::inplace_merge(first, middle, last);
    }
}

int main()
{
    std::vector<int> v{8, 2, -2, 0, 11, 11, 1, 7, 3};
    merge_sort(v.begin(), v.end());
    for (const auto& n : v)
        std::cout << n << ' ';
    std::cout << '\n';
}

Вывод:

-2 0 1 2 3 7 8 11 11

Смотрите также

объединяет два отсортированных диапазона
(шаблон функции & объект функции алгоритма)
сортирует диапазон элементов
(шаблон функции & объект функции алгоритма)
сортирует диапазон элементов с сохранением относительного порядка эквивалентных элементов
(шаблон функции & объект функции алгоритма)
объединяет два упорядоченных диапазона на месте
(объект функции алгоритма)