Алгоритм Нарайаны

Материал из testwiki
Версия от 23:36, 17 мая 2020; imported>Positivealex (отмена правки 107101767 участника 93.100.75.148 (обс.) + добавление ссылки на реализации)
(разн.) ← Предыдущая версия | Текущая версия (разн.) | Следующая версия → (разн.)
Перейти к навигации Перейти к поиску

Алгори́тм Нарайа́ны — нерекурсивный алгоритм, генерирующий по данной перестановке следующую за ней перестановку (в лексикографическом порядке). Придуман индийским математиком Шаблон:Нп5 в XIV веке.

Если алгоритм Нарайаны применить в цикле к исходной последовательности из n элементов a1,a2,...,an, упорядоченных так, что a1a2...an, то он сгенерирует все перестановки элементов множества {a1,a2,...,an} в лексикографическом порядке.

Другой особенностью алгоритма является то, что необходимо запоминать только один элемент перестановки.

Алгоритм

  • Шаг 1: найти такой наибольший j, для которого aj<aj+1.
  • Шаг 2: увеличить aj. Для этого надо найти наибольшее l>j, для которого al>aj. Затем поменять местами aj и al.
  • Шаг 3: записать последовательность aj+1,...,an в обратном порядке.

Оценка сложности

В случае перестановки, где элементы перемешаны случайным образом, сложность алгоритма практически не зависит от количества элементов. В приведённых реализациях производится в среднем 3 сравнения элементов перестановки и 2.17 обменов.

Наилучшим является случай, когда предпоследний элемент перестановки больше последнего, тогда производится 2 сравнения и 1 обмен. Худшим является случай, когда элементы перестановки отсортированы по убыванию, и, если длина перестановки равна n, то производится n+1 сравнений и n/2+1 обменов.

В целом сложность алгоритма можно оценить как O(n).

Литература

Шаблон:Wikibooks

Шаблон:Нет источников Шаблон:Rq