Перестановкою порядку називається послідовність p = (p[1], p[2], \ldots, p[n]), в якій кожне число від до зустрічається рівно один раз. Зручно розглядати перестановку як відображення, що переводить число у число : i \to p[i].
Оберненою до перестановки називається перестановка p^{-1}, яка повертає кожне число на своє місце: якщо переводить у , то p^{-1} переводить назад у . Іншими словами, для всіх виконується рівність:
Ця рівність одразу дає алгоритм: число має стояти на позиції оберненої перестановки. Переберемо всі від до і для кожного з них виконаємо присвоєння pi[p[i]] = i, де масив зберігає обернену перестановку.
Кожна позиція масиву заповнюється рівно один раз. Дійсно, значення p[1], p[2], \ldots, p[n] попарно різні та охоплюють усі числа від до , тому індекси також попарно різні та охоплюють усі позиції від до .
Дворядковий запис. Перестановку часто записують у два рядки: у верхньому рядку стоять числа 1, 2, \ldots, n, а під кожним числом стоїть значення . Щоб отримати обернену перестановку, достатньо поміняти рядки місцями та відсортувати стовпці за зростанням верхнього рядка.
Приклад
Розглянемо перестановку з прикладу. Запишемо її та обернену до неї перестановку у дворядковому вигляді:
Знайдемо p^{-1} за формулою pi[p[i]] = i:
Отримуємо p^{-1} = (3, 1, 2). Дворядковий запис дає той самий результат: поміняв рядки перестановки місцями, отримуємо стовпці , , . Відсортувавши їх за верхнім рядком, отримуємо нижній рядок .
На малюнку перестановка зображена у вигляді стрілок i \to p[i]. В оберненій перестановці всі стрілки вказують у протилежному напрямку: p[i] \to i.
Реалізація алгоритму
Масив зберігає вхідну перестановку, а масив зберігає обернену перестановку.
#define MAX 20010
int p[MAX], pi[MAX];Зчитаємо вхідну перестановку.
scanf("%d",&n);
for(i = 1; i <= n; i++)
scanf("%d",&p[i]);Обчислимо обернену перестановку.
for(i = 1; i <= n; i++)
pi[p[i]] = i;Виведемо обернену перестановку.
for(i = 1; i <= n; i++)
printf("%d ",pi[i]);
printf("\n");Реалізація мовою Python
Список зберігає вхідну перестановку, а список зберігає обернену перестановку. Зчитаємо вхідні дані.
n = int(input())
p = [0] + list(map(int, input().split()))
pi = [0] * (n + 1)Обчислимо обернену перестановку.
for i in range(1, n + 1):
pi[p[i]] = iВиведемо обернену перестановку.
for i in range(1, n + 1):
print(pi[i], end=" ")
print()