Oto odpowiedź opracowana w oparciu o algorytm z artykułu, do którego link dołączył Joe: http://arxiv.org/abs/0805.1598
Najpierw zastanówmy się nad algorytmem , który wykorzystuje dziel i zwyciężaj.Θ(nlogn)
1) Dziel i rządź
Dano nam
a1,a2,…,b1,b2,…bn
Teraz, aby użyć dzielenia i podbijania, dla niektórych , staramy się uzyskać tablicęm=Θ(n)
[a1,a2,…,am,b1,b2,…,bm],[am+1,…,an,bm+1,…bn]
i powtórzyć.
Zauważ, że część to cykliczne przesunięcieb1,b2,…bm,am+1,…an
am+1,…an,b1,…bm
przez miejsc.m
Jest to klasyk i można tego dokonać na miejscu poprzez trzy cofnięcia w czasie .O(n)
Zatem dziel i rządź daje ci algorytm z rekurencją podobną do .Θ(nlogn)T(n)=2T(n/2)+Θ(n)
2) Cykle permutacji
Teraz innym podejściem do problemu jest rozważenie permutacji jako zestawu rozłącznych cykli.
Permutacja jest podawana przez (przy założeniu, że od )1
j↦2jmod2n+1
Gdybyśmy w jakiś sposób wiedzieli dokładnie, czym są cykle, wykorzystując stałą dodatkową przestrzeń, moglibyśmy zrealizować permutację, wybierając element , określić, dokąd ten element idzie (używając powyższej formuły), umieścić element w docelowej lokalizacji w przestrzeni tymczasowej, umieścić element do tej docelowej lokalizacji i kontynuuj cykl. Gdy skończymy z jednym cyklem, przechodzimy do elementu następnego cyklu i podążamy za nim i tak dalej.AA
To dałoby nam algorytm czasowy , ale zakłada, że „jakoś wiedzieliśmy, jakie dokładnie są cykle” i staramy się wykonywać tę księgowość w ramach ograniczenia przestrzeni to sprawia, że ten problem jest trudny.O(n)O(1)
W tym miejscu papier wykorzystuje teorię liczb.
Można wykazać, że w przypadku, gdy , elementy w pozycjach , są w różnych cyklach i każdy cykl zawiera element w pozycji .2n+1=3k13,32,…,3k−13m,m≥0
Wykorzystuje to fakt, że jest generatorem .2(Z/3k)∗
Tak więc, gdy , podążanie za cyklem daje nam algorytm czasowy , ponieważ dla każdego cyklu wiemy dokładnie, od czego zacząć: potęgi (w tym ) (te można obliczyć w spacji ).2n+1=3kO(n)31O(1)
3) Ostateczny algorytm
Teraz łączymy dwa powyższe: Divide and Conquer + Permutation Cycles.
Wykonujemy dzielenie i podbijać, ale wybrać tak, jest potęgą i .m2m+13m=Θ(n)
Dlatego zamiast rekurencji na obu „połówkach”, powtarzamy tylko na jednej i wykonujemy dodatkową pracę.Θ(n)
To daje nam powtarzalność (dla niektórych ), a tym samym daje nam czas , algorytm kosmiczny!T(n)=T(cn)+Θ(n)0<c<1O(n)O(1)