Некоторый дополнительный материал (я немного пьян, мне, вероятно, придется отредактировать это завтра, поэтому возьмите его с крошкой соли):
Кнут и Седжвик оба покрывали перестановки эоны назад.
Посмотрите на: http://www.princeton.edu/~rblee/ELE572Papers/p137-sedgewick.pdf
Для n предметов у вас есть n! перестановок, так что для 13 предметов у вас уже есть 6 227 020 800 перестановок. Поэтому создание всех перестановок для большого набора предметов станет довольно быстрым.
Существует в основном два набора алгоритмов для создания перестановок: методы ранжирования / отстранения и постепенного изменения.
При ранжировании / отмене рейтинга у вас есть два метода: ранга и отмены.
Ранг даст вам положение перестановки в порядке генерации.
Unrank даст вам перестановку, которая лежит в целом числе m, с 0> = m <= <strong>n! и n количеством элементов, для которых вы хотите создать перестановки.
Это полезно для различных случаев, таких как:
Создание случайной перестановки (вы просто создаете случайное число от 0 до n! И вызываете unrank (randomNumber)) и получаете перестановку в позиции randomNumber.
Создание последовательностей, получение следующей перестановки: у вас есть перестановка p и вызов Rank (p), затем Unrank (rank + 1).
Методы инкрементальных изменений:
Они в основном работают через свопинг и более эффективны, чем ранжирование / отмена рейтинга:
Из википедии, неупорядоченное поколение:
function permutation(k, s) {
for j = 2 to length(s) {
swap s[(k mod j) + 1] with s[j]; // note that our array is indexed starting at 1
k := k / j; // integer division cuts off the remainder
}
return s;
}