您的位置:首页 > 其它

Ural1024 Permutations

2013-10-29 10:51 225 查看
Input

Input

In the first line of the standard input an only natural number N (1 <= N <= 1000) is contained, that is a number of elements in the set that is rearranged by this permutation. In the second line there are N natural numbers of the range from 1 up to N, separated
by a space, that define a permutation — the numbers P(1), P(2),…, P(N).

第一行包含一个自然数 N (1 <= N <= 1000), N 是置换的元素个数。第二行是 N 个范围为1到N的自然数,用空格隔开,分别表示 P(1), P(2),…, P(N)。

Output

You should write an only natural number to the standard output, that is an order of the permutation. You may consider that an answer shouldn’t exceed 109.

输出置换的顺序,结果不超过10^9。

Sample Input
5

4 1 5 2 3

Sample Output

6

       这题要将原序列经过给定序列的变换变回原样,那么在序列中必定会出现若干个循环。
       比如说样例吧,有两个循环,1--> 4 --> 2 -->1,3--> 5 --> 3。要让所有循环一同回到初始状态,则最小次数必定是所有循环的最小公倍数,又知两数的最小公倍数=两数相乘再除以两数的最大公约数。

CODE:

var
v:array[0..1000] of boolean;
size,pre,now,son:array[0..1000] of longint;
lian,n,tot:longint;

procedure add(a,b:longint);
begin
inc(tot); pre[tot]:=now[a]; now[a]:=tot; son[tot]:=b;
end;

function gcd(a,b:longint):longint;
begin
if b=0 then gcd:=a
else
gcd:=gcd(b, a mod b);
end;

procedure dfs(x:longint);
var p:longint;
begin
v[x]:=true;
inc(size[lian]);
p:=now[x];
while p>0 do
begin
if not v[son[p]] then
dfs(son[p]);
p:=pre[p];
end;
end;

procedure init;
var i,j,k,ans,a,b:longint;
begin
readln(n); tot:=0;
for i:=1 to n do
begin
read(a);
add(i,a);
end;

for i:=1 to n do
if not v[i] then
begin
inc(lian);
dfs(i);
end;

if lian=1 then writeln(size[1])
else
begin
ans:=size[1]*size[2] div gcd(size[1],size[2]);
for i:=3 to lian do
ans:=ans*size[i] div gcd(ans,size[i]);

writeln(ans);
end;
end;

begin
init;
end.
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: