Skip to content

Instantly share code, notes, and snippets.

@Koitaro
Created September 16, 2011 15:49
Show Gist options
  • Select an option

  • Save Koitaro/1222410 to your computer and use it in GitHub Desktop.

Select an option

Save Koitaro/1222410 to your computer and use it in GitHub Desktop.
CHR : Project Euler 300-
:- use_module(library(chr)).
:- chr_option(optimize, full).
:- chr_type list(T) ---> []; [T|list(T)].
:- chr_type heap(T) ---> int-list(heap(T)).
:- chr_constraint
heap(+heap(int)),
next(+int,+int,+int),
way(+int),
cube(+int,+int,+int),
diff(+int),
count(+int,+int),
check,
answer(+int),
sum(+int),
problem348.
problem348 <=> heap(1-[]), heap(11-[]), next(2,2,22).
answer(A), answer(B), answer(C), answer(D), answer(E)
<=> X is A+B+C+D+E, sum(X).
sum(_) \ next(_,_,_) <=> true.
sum(_) \ heap(_) <=> true.
heap(A-L), heap(B-M) <=> A =< B | heap(A-[B-M|L]).
tail([H|T]) :- heap(H), tail(T).
tail([]) :- !.
next(_,N,_) \ heap(H-T) <=> N > H | way(H), tail(T).
next(N,X,Y) <=> heap(X-[]), heap(Y-[]),
N1 is N+1, gen(N1,X1,Y1), next(N1,X1,Y1).
way(N) <=> cube(N,1,1), count(N,0), check.
cube(N,_,B) <=> N =< B | true.
cube(N,A,B) <=> X is N-B, diff(X), A1 is A+1, B1 is A1**3, cube(N,A1,B1).
diff(N) <=> floor(sqrt(N),R), R**2 =\= N | true.
diff(_) # passive, count(N,X) <=> X1 is X+1, count(N,X1).
count(N,4), check <=> answer(N), write(N), nl.
count(_,_), check <=> true.
gen(N,X,Y) :-
i2d(N,L), reverse(L,[H|T]),
append(L,T,L1), d2i(L1,X),
append(L,[H|T],L2), d2i(L2,Y).
i2d(N,X) :- i2d(N,[],X).
i2d(0,X,X) :- !.
i2d(N,L,X) :- N1 is N//10, N2 is N rem 10, i2d(N1,[N2|L],X).
d2i(L,X) :- d2i(L,0,X).
d2i([],X,X) :- !.
d2i([H|T],N,X) :- N1 is N*10+H, d2i(T,N1,X).
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment