Сортировка с помощью обменов
Сортировки с помощью обменов основываются на сравнении двух элементов. Если порядок элементов не соответствует упорядоченности, то происходит их обмен. Процесс повторяется до тех пор, пока элементы не будут упорядочены.
Следует отметить, что и для рассмотренных ранее алгоритмов также имел место обмен элементов, однако в рассматриваемом типе алгоритмов обмен местами двух элементов представляет собой характернейшую особенность процесса.
Пузырьковая сортировка
Алгоритм заключается в просмотре исходной последовательности справа налево, и при каждом шаге меньший из двух соседних элементов перемещается к левой позиции. В результате первого просмотра самый маленький элемент будет находиться в крайней левой позиции. После этого повторяем описанный выше процесс, рассматривая в качестве исходной последовательности массив, начиная со 2- й позиции и т. д.
Оценим трудоемкость приведенного выше алгоритма пузырьковой сортировки.
Перемещение минимального из п элементов в крайнюю левую позицию требует в худшем случаеС∙(n-1) операций (число сравнений ключей не зависит от порядка элементов; число присваиваний минимально, если элементы упорядочены, и максимально, если они расположены в обратном порядке).
Рекуррентное уравнение будет иметь следующий вид:
Т(n) = С • (n- 1) + Т(n- 1),T(1) = 0.
Алгоритм пузырьковой сортировки имеет трудоемкость 0(п2).
Шейкерная сортировка
Анализ алгоритма пузырьковой сортировки приводит к следующим наблюдениям.
1. Если при некотором из проходов нет перестановок, то алгоритм можно завершить.
2. Если зафиксировать индекс к последнего обмена (все пары левее этого индекса уже упорядочены), то просмотр можно завершить на этом индексе, а не идти до нижнего предела для индексаi.
3. Чередование направлений для просмотра (всплывает самый легкий, а тонет самый тяжелый).
Шейкерная сортировка с успехом используется в тех случаях, когда известно, что элементы почти упорядочены.
Сортировка слиянием
Сортировка слиянием заключается в следующем.
1.Делим последовательность элементов на две части.
2.Сортируем отдельно каждую из частей.
3.Производим слияние отсортированных частей последовательности (при слиянии сравниваем наименьшие элементы и меньший из них отправляем в список вывода; повторяем описанные действия до тех пор, пока не исчерпается одна из частей; все оставшиеся элементы другой части пересылаем в список вывода).
Рекуррентное уравнение алгоритма сортировки слиянием имеет вид:
Т(n) = 2T(n/2) + Сn.
По теореме о решении рекуррентного уравнения трудоемкость описанного алгоритма есть O(пlog п).
Сортировка с помощью разделения
Данный алгоритм сортировки был разработан Ч. Хоаром и является одним из самых быстрых методов сортировки массива. Данный алгоритм часто называют быстрой сортировкой (Quicksort).
Суть алгоритма состоит в следующем.
1. Выбрать некоторый элемент х для сравнения (это может быть средний, первый или последний элемент).
2. Используя обмены, выполнить процедуру разделения, суть которой заключается в следующем: разбить массив на две части: левую с ключами ≤ х и правую с ключами ≥х . Данные действия могут быть выполнены, например, следующим алгоритмом:
- просматриваем массив слева, пока не встретим элемент а[i] > х;
- просматриваем массив справа, пока не встретим элемент a[j] <х;
- меняем местами эти два элемента;
- продолжаем просмотр и обмен до тех пор, пока не будут просмотрены все элементы массива (г > j).
3. Повторить процедуру разделения к получившимся двум частям, затем к частям частей и так далее, пока каждая из частей не будет состоять из одного единственного элемента.
Построим рекуррентное уравнение для алгоритма быстрой сортировки.
Процедура разделения n элементов требует Сп операций, так как каждый элемент последовательности необходимо сравнить с выбранным элементом, поэтому рекуррентное уравнение будет иметь вид:
T(n)=Cn+T(│A1│) +T(│A2│),
где │A1│— размер левой части массива после процедуры разделения,│А2│ — размер правой части массива после процедуры разделения.
Если предположить, что разделение в среднем разбивает часть пополам, то
Т(n) = Сn+ 2T(n/2)
и по теореме о решении рекуррентного уравнения трудоемкость алгоритма быстрой сортировки в среднем есть O(п logп).
Худшим случаем является ситуация, когда в качестве сравниваемого элемента выбирается наибольший из всех элементов рассматриваемой части. В этом случае после процедуры разделения │A1│ =n- 1 и│А2│ = 1.
Рекуррентное уравнение будет иметь вид:
T(n) = Сn+T(n-1) +T(1)
и трудоемкость алгоритма быстрой сортировки в худшем случае есть 0(п2).
Сам Ч. Хоар предполагает, что х надо выбирать случайно, а для небольших выборок останавливаться на медиане.