app([],L,L). app([E|R],L,[E|RL]) :- app(R,L,RL). % Simple meta-interpreter for Prolog: prove(true) :- !. prove( (G1,G2) ) :- !, prove(G1), prove(G2). prove(L) :- clause(L,G), prove(G). % A meta-interpreter for Prolog which also computes the proof length: lprove(true,0) :- !. lprove( (G1,G2), N) :- !, lprove(G1,N1), lprove(G2,N2), N is N1+N2. lprove(L,N) :- clause(L,G), lprove(G,N1), N is N1+1. % Simple meta-interpreter for Prolog with tracing. tprove(true) :- !. tprove( (G1,G2) ) :- !, tprove(G1), tprove(G2). tprove(L) :- showcallfail(L), clause(L,G), tprove(G), showexitredo(L). showcallfail(L) :- write('CALL: '), write(L), nl. showcallfail(L) :- write('FAIL: '), write(L), nl, fail. showexitredo(L) :- write('EXIT: '), write(L), nl. showexitredo(L) :- write('REDO: '), write(L), nl, fail. p(a). p(b). q(b). s(X) :- p(X), q(X).