|
@@ -1,3 +1,4 @@
|
|
|
+program fannkuch;
|
|
|
{ The Computer Language Shootout
|
|
|
http://shootout.alioth.debian.org/
|
|
|
|
|
@@ -25,21 +26,12 @@ procedure swap(var a, b: longint); inline;
|
|
|
var tmp: longint;
|
|
|
begin tmp := a; a := b; b := tmp end;
|
|
|
|
|
|
-procedure roll_down( var a : array of longint ); inline;
|
|
|
-var tmp : longint;
|
|
|
-begin
|
|
|
- tmp := a[ 0 ];
|
|
|
- move( a[1], a[0], high(a)*sizeof(longint) );
|
|
|
- a[ high(a) ] := tmp;
|
|
|
-end;
|
|
|
-
|
|
|
-
|
|
|
-procedure reverse( var a: array of longint ); inline;
|
|
|
+procedure reverse( k: longint); inline;
|
|
|
var
|
|
|
pi, pj : pLongint;
|
|
|
begin
|
|
|
- pi := @a[0];
|
|
|
- pj := @a[high(a)];
|
|
|
+ pi := @permu_copy[1];
|
|
|
+ pj := @permu_copy[k-1];
|
|
|
while pi<pj do
|
|
|
begin
|
|
|
swap(pi^, pj^);
|
|
@@ -51,6 +43,8 @@ end;
|
|
|
function NextPermutation: boolean;
|
|
|
var
|
|
|
r0: longint;
|
|
|
+ tmp: LongInt;
|
|
|
+ i : longint;
|
|
|
begin
|
|
|
r0 := r; // use local variable
|
|
|
NextPermutation := true;
|
|
@@ -60,7 +54,11 @@ begin
|
|
|
NextPermutation := false;
|
|
|
break;
|
|
|
end;
|
|
|
- roll_down( permu[ 0 .. r0 ] );
|
|
|
+ tmp := permu[0];
|
|
|
+ for i := 1 to r0 do
|
|
|
+ permu[i-1] := permu[i];
|
|
|
+ permu[r0] := tmp;
|
|
|
+
|
|
|
dec(count[r0]);
|
|
|
if count[r0] > 0 then
|
|
|
break;
|
|
@@ -69,9 +67,26 @@ begin
|
|
|
r := r0;
|
|
|
end;
|
|
|
|
|
|
+function countflips: integer; inline;
|
|
|
+var
|
|
|
+ last: LongInt;
|
|
|
+ tmp: LongInt;
|
|
|
+begin
|
|
|
+ countflips := 0;
|
|
|
+ last := permu_copy[0];
|
|
|
+ repeat
|
|
|
+ // Reverse part of the array.
|
|
|
+ reverse(last);
|
|
|
+ tmp := permu_copy[ last ];
|
|
|
+ permu_copy[ last ] := last;
|
|
|
+ last := tmp;
|
|
|
+ inc(countflips);
|
|
|
+ until last = 0;
|
|
|
+end;
|
|
|
+
|
|
|
function fannkuch: longint;
|
|
|
var
|
|
|
- print30, m, i, last, tmp, flips: longint;
|
|
|
+ print30, m, i, flips: longint;
|
|
|
begin
|
|
|
print30 := 0;
|
|
|
fannkuch := 0;
|
|
@@ -84,8 +99,10 @@ begin
|
|
|
repeat
|
|
|
if print30 < 30 then
|
|
|
begin
|
|
|
- for i := 0 to m do write(permu[i] + 1);
|
|
|
- writeln; inc(print30);
|
|
|
+ for i := 0 to m do
|
|
|
+ write(permu[i] + 1);
|
|
|
+ writeln;
|
|
|
+ inc(print30);
|
|
|
end;
|
|
|
while r <> 1 do
|
|
|
begin
|
|
@@ -95,18 +112,7 @@ begin
|
|
|
if (permu[0]<>0) and (permu[m]<>m) then
|
|
|
begin
|
|
|
move(permu[0], permu_copy[0], sizeof(longint)*n);
|
|
|
- flips := 0;
|
|
|
-
|
|
|
- last := permu_copy[0];
|
|
|
- repeat
|
|
|
- // Reverse part of the array.
|
|
|
- reverse( permu_copy[ 1 .. last-1 ] );
|
|
|
- tmp := permu_copy[ last ];
|
|
|
- permu_copy[ last ] := last;
|
|
|
- last := tmp;
|
|
|
- inc(flips);
|
|
|
- until last = 0;
|
|
|
-
|
|
|
+ flips := countflips;
|
|
|
if flips > fannkuch then
|
|
|
fannkuch := flips;
|
|
|
end;
|