如果发现广告等破坏行为,请尽量将条目恢复到较早的版本而不是把相应内容直接删除,谢谢合作。
URAL/1024
来自"NOCOW"
< URAL
做这道题的时候要有一点群论的基础,把给定的置换拆成若干个循环,这个置换的顺序(即k值)就是各个循环的顺序的最小公倍数,各个循环的顺序就是他的长度(即元素个数)(这个在草稿纸上算一下就知道了)。
program cao; const maxn=1000; var data,lcm:array[0..maxn] of longint; flag:array[0..maxn] of boolean; a,b,c,d,e,f,g,h,i,j,k,l,n,m,p,q,ans:longint; function gcd(a,b:longint):longint; begin if b=0 then exit(a); exit(gcd(b,a mod b)); end; procedure init; begin read(n); for i:=1 to n do read(data[i]); end; procedure main; begin p:=0; for i:=1 to n do if flag[i]=false then begin j:=i; k:=0; while flag[j]=false do begin inc(k); flag[j]:=true; j:=data[j]; end; inc(p); lcm[p]:=k; end; ans:=1; for i:=1 to p do ans:=ans*lcm[i] div gcd(ans,lcm[i]); end; procedure print; begin writeln(ans); end; begin init; main; print; end.
LS+1,其实就是所有循环节的最小公倍数。
Program P1024; Var n,top : Longint; p,lit : Array [1..1000] of Integer; use : Array [1..1000] of Boolean; Procedure Init; var a : Longint; begin readln(n); for a:=1 to n do read(p[a]);readln; end; Procedure DFS(tn,sum:Longint); begin inc(sum); use[tn]:=True; if use[p[tn]] then begin inc(top);lit[top]:=sum;Exit;end; DFS(p[tn],sum); end; Procedure Main; var a : Longint; begin Fillchar(use,sizeof(use),False); for a:=1 to n do if not(use[a]) then DFS(a,0); end; Function gcd(p,q:Longint):Longint; begin if q=0 then Exit(p); Exit(gcd(q,p mod q)); end; Function GetLcm:Longint; var a,ans : Longint; begin ans:=lit[1]; for a:=2 to top do ans:=(ans*lit[a]) Div gcd(ans,lit[a]); Exit(ans); end; Procedure Print; begin writeln(GetLcm); end; Begin Init; Main; Print; End.