第Iカードの位置が[I]にカードのi番目の位置の交換後、[I]です。
交換など交換後の全ての配列位置、
既知の配列のm回交換した後、元のシーケンスを見つけます。
考える:
与えられた[i]は4756123です
変換したら、
1 2 3 4 5 6 7 7 4 5 6 1 2 3 1 2 3 4 5 6 7
* =
4 7 5 6 1 2 3 6 3 1 2 4 7 5 6 3 1 2 4 5 7
二次変換
1,234,567,631,247,512,345。6. 7
* =
6 3 1,247,571,632,547,163,254
形質転換は3回行った
。1 2 3,456,771,632,541,234,567
* =
7 1 6 3 2 5 4 4 5 6 7 1 2 3 4 5 6 7 1 2 3
変換は、4756123を得るために3回行った後に
元の配列は、形質転換の際に第3のサイクルを発生します
一般的なケースを考えてみましょう。
元のシーケンス1〜N個の異なる数字なので、シーケンスは、少なくとも一つの置換基を含むことができ
、多くの形質転換後に肯定した後、
そこを循環する、される
と、今、私たちは、交換サイクルのセクションを見つけ、新しいシーケンスが知られており、交換、数
その後、RES - S%RES
二次スワップは、元の配列を取得します。
//は、循環節をresは、Sは、変換、分析の数であります
する#include <stdio.hに> する#include <string.hの> INT配列[1010]、ArrayA [1010]、ArrayB [1010]。 ボイドGetNextの(INT N) { ため(INT iが= 1; I <= N; I ++) ArrayB [I] = ArrayA [ArrayA [I]]。 以下のために(INT I 1 =; I <= N; I ++) ArrayA [I] = ArrayB [I]。 } BOOL IsSame(INT N) { ための(iは1 = INT; iが<= N; iが++) (ArrayB [I] =配列[I]!)もし 戻り偽。 trueを返します。 } int型のmain() { int型N、S。 (〜scanf関数は( "%D%D"、&N、&S))しながら { ため(; <I = N;整数iが1 = I ++) { scanf関数( "%のD"、および配列[I])。 ArrayA [I] =配列[i]は、 } int型RES。 用(RES = 1 ;; RES ++) { GetNextの(N)。 (IsSame(N))であれば ブレーク。 } INT M = RES - S%のRES。 int型NUM = 0; 一方、(NUM <M) { GetNextの(N)。 NUM ++; } ため(INT I 1 =; I <= N; I ++) のprintf( "%D \ n"は、ArrayB [I])。 } 0を返します。 } ---------------- 免責事項:この記事はCSDNブロガー徒歩Shaonianラングのオリジナルの記事で、CC 4.0 BY-SAの著作権契約書に従ってください、複製、オリジナルのソースを添付してくださいリンクとこの文。 原文链接:HTTPS://blog.csdn.net/lianai911/article/details/39323335