RosettaCodeData/Task/Ackermann-function/Picat/ackermann-function.picat

39 lines
865 B
Plaintext

go =>
foreach(M in 0..3)
println([m=M,[a(M,N) : N in 0..16]])
end,
nl,
printf("a2(4,1): %d\n", a2(4,1)),
nl,
time(check_larger(3,10000)),
nl,
time(check_larger(4,2)),
nl.
% Using a2/2 and chop off large output
check_larger(M,N) =>
printf("a2(%d,%d): ", M,N),
A = a2(M,N).to_string,
Len = A.len,
if Len < 50 then
println(A)
else
println(A[1..20] ++ ".." ++ A[Len-20..Len])
end,
println(digits=Len).
% Plain tabled (memoized) version with guards
table
a(0, N) = N+1 => true.
a(M, 0) = a(M-1,1), M > 0 => true.
a(M, N) = a(M-1,a(M, N-1)), M > 0, N > 0 => true.
% Faster and pure function version (no guards).
% (Based on Python example.)
table
a2(0,N) = N + 1.
a2(1,N) = N + 2.
a2(2,N) = 2*N + 3.
a2(3,N) = 8*(2**N - 1) + 5.
a2(M,N) = cond(N == 0,a2(M-1, 1), a2(M-1, a2(M, N-1))).