|
|
pl:prolog:pllib:skeleton [2019/06/27 15:50] |
pl:prolog:pllib:skeleton [2019/06/27 15:50] (aktualna) |
| ====== Skeleton ====== |
| {{tag>misc}} |
| ===== Description ===== |
| Composing two enhancements of a skeleton |
| |
| **Source**: The Art of Prolog |
| ===== Download ===== |
| Program source code: {{skeleton.pl}} |
| ===== Listing ===== |
| <code prolog> |
| /* |
| compose(Program1,Program2,Skeleton,FinalProgram) :- |
| FinalProgram is the result of composing Program1 and |
| Program2, which are both enhancements of Skeleton. |
| */ |
| |
| :- op(40,xfx,\). |
| |
| compose([Cl1|Cls1],[Cl2|Cls2],[ClSkel|ClsSkel],[Cl|Cls]) :- |
| compose_clause(Cl1,Cl2,ClSkel,Cl), |
| compose(Cls1,Cls2,ClsSkel,Cls). |
| compose([ ],[ ],[ ],[ ]). |
| |
| compose_clause((A1 :- B1),(A2 :- B2),(ASkel :- BSkel),(A :- B)) :- |
| composition_specification(A1,A2,ASkel,A), |
| compose_bodies(BSkel,B1,B2,B\true). |
| |
| compose_bodies(SkelBody,Body1,Body2,B\BRest) :- |
| first(SkelBody,G), !, |
| align(G,Body1,G1,RestBody1,B\B1), |
| align(G,Body2,G2,RestBody2,B1\(Goal,B2)), |
| compose_goal(G1,G2,Goal), |
| rest(SkelBody,Gs), |
| compose_bodies(Gs,RestBody1,RestBody2,B2\BRest). |
| compose_bodies(true,Body1,Body2,B\BRest) :- |
| rest_goals(Body1,B\B1), rest_goals(Body2,B1\BRest). |
| |
| align(Goal,Body,G,RestBody,B\B) :- |
| first(Body,G), correspond(G,Goal), !, rest(Body,RestBody). |
| align(Goal,(G,Body),CorrespondingG,RestBody,(G,B)\B1) :- |
| align(Goal,Body,CorrespondingG,RestBody,B\B1). |
| |
| first((G,Gs),G). |
| first(G,G) :- G \== (A,B), G \== true. |
| |
| rest((G,Gs),Gs). |
| rest(G,true) :- G \== (A,B). |
| |
| correspond(G,G). |
| correspond(G,B) :- map(G,B). |
| |
| compose_goal(G,G,G) :- !. |
| compose_goal(A1,A2,A) :- |
| !, composition_specification(A1,A2,ASkel,A). |
| |
| rest_goals(true,B\B) :- !. |
| rest_goals(Body,(G,B)\BRest) :- |
| first(Body,G), !, rest(Body,Body1), rest_goals(Body1,B\BRest). |
| |
| % Program 18.6: Composing two enhancements of a skeleton |
| </code> |
| ===== Comments ===== |
| |