Logic Programming (cont’d): Lists Lists in Prolog are represented by a functor (similar to cons in Scheme): 1.The empty list is represented by the constant.

Slides:



Advertisements
Similar presentations
CS4026 Formal Models of Computation Part II The Logic Model Lecture 6 – Arithmetic, fail and the cut.
Advertisements

Prolog for Dummies Ulf Nilsson Dept of Computer and Information Science Linköping University.
Prolog.
Determinacy Inference for Logic Programs Lunjin Oakland University In collaboration with Andy Kent University, UK.
CSA2050: DCG I1 CSA2050 Introduction to Computational Linguistics Lecture 8 Definite Clause Grammars.
Logic Programming – Part 2 Lists Backtracking Optimization (via the cut operator) Meta-Circular Interpreters.
Logic Programming – Part 2 Lists Backtracking Optimization (via the cut operator) Meta-Circular Interpreters.
C O N T E X T - F R E E LANGUAGES ( use a grammar to describe a language) 1.
Inference and Reasoning. Basic Idea Given a set of statements, does a new statement logically follow from this. For example If an animal has wings and.
Closure Properties of CFL's
Answer Set Programming Overview Dr. Rogelio Dávila Pérez Profesor-Investigador División de Posgrado Universidad Autónoma de Guadalajara
Patterns in ML functions. Formal vs. actual parameters Here's a function definition (in C): –int add (int x, int y) { return x + y; } –x and y are the.
Functional Design and Programming Lecture 11: Functional reasoning.
Introduction to Computability Theory
1 Introduction to Computability Theory Lecture7: PushDown Automata (Part 1) Prof. Amos Israeli.
UNIVERSITY OF SOUTH CAROLINA Department of Computer Science and Engineering Controlling Backtracking Notes for Ch.5 of Bratko For CSCE 580 Sp03 Marco Valtorta.
Constraint Logic Programming Ryan Kinworthy. Overview Introduction Logic Programming LP as a constraint programming language Constraint Logic Programming.
0 PROGRAMMING IN HASKELL Chapter 7 - Higher-Order Functions.
Comp 205: Comparative Programming Languages Lazy Evaluation and Infinite Lists Lecture notes, exercises, etc., can be found at:
0 PROGRAMMING IN HASKELL Chapter 6 - Recursive Functions Most of this should be review for you.
0 PROGRAMMING IN HASKELL Chapter 6 - Recursive Functions.
Context-Free Grammar CSCI-GA.2590 – Lecture 3 Ralph Grishman NYU.
Formal Models of Computation Part II The Logic Model
The Theory of NP-Completeness 1. What is NP-completeness? Consider the circuit satisfiability problem Difficult to answer the decision problem in polynomial.
FATIH UNIVERSITY Department of Computer Engineering Controlling Backtracking Notes for Ch.5 of Bratko For CENG 421 Fall03.
CS 321 Programming Languages and Compilers Prolog part 2.
DECIDABILITY OF PRESBURGER ARITHMETIC USING FINITE AUTOMATA Presented by : Shubha Jain Reference : Paper by Alexandre Boudet and Hubert Comon.
Logic Programming (cont’d): Lists Lists in Prolog are represented by a functor (similar to cons in Scheme): 1.The empty list is represented by the constant.
Lee CSCE 314 TAMU 1 CSCE 314 Programming Languages Haskell: Types and Classes Dr. Hyunyoung Lee.
1 COMP 205 Introduction to Prolog Dr. Chunbo Chu Week 14.
A Second Look At ML 1. Outline Patterns Local variable definitions A sorting example 2.
Logic Programming (cont’d): Lists Lists in Prolog are represented by a functor (similar to cons in Scheme): 1.The empty list is represented by the constant.
CS535 Programming Languages Chapter - 10 Functional Programming With Lists.
Automated Reasoning Early AI explored how to automated several reasoning tasks – these were solved by what we might call weak problem solving methods as.
Automated Reasoning Early AI explored how to automate several reasoning tasks – these were solved by what we might call weak problem solving methods as.
Full Logic Programming. Data structures Pure LP allows only to represent relations (=predicates) To obtain full LP we will add functors (=function symbols)
Curry A Tasty dish? Haskell Curry!. Curried Functions Currying is a functional programming technique that takes a function of N arguments and produces.
CS 152: Programming Language Paradigms March 12 Class Meeting Department of Computer Science San Jose State University Spring 2014 Instructor: Ron Mak.
Chapter SevenModern Programming Languages1 A Second Look At ML.
1 Section 13.1 Turing Machines A Turing machine (TM) is a simple computer that has an infinite amount of storage in the form of cells on an infinite tape.
C H A P T E R N I N E Logic Programming Part 2 Programming Languages – Principles and Paradigms by Allen Tucker, Robert Noonan.
1 Turing Machines and Equivalent Models Section 13.1 Turing Machines.
Recursion ITI 1121 N. El Kadri. Reminders about recursion In your 1 st CS course (or its equivalent), you have seen how to use recursion to solve numerical.
Defining Classes Modules and ADTs CSCE 314 Spring 2016.
C. Varela1 Logic Programming (PLP 11, CTM 9.3) Prolog Imperative Control Flow: Backtracking, Cut, Fail, Not Lists, Append Carlos Varela Rennselaer Polytechnic.
Section Recursion  Recursion – defining an object (or function, algorithm, etc.) in terms of itself.  Recursion can be used to define sequences.
Section 16.5, 16.6 plus other references
Logic Programming: Introduction
Pushdown Automata.
Introduction to Logic for Artificial Intelligence Lecture 2
Logic Programming (cont’d): Lists
PROGRAMMING IN HASKELL
PROGRAMMING IN HASKELL
PROGRAMMING IN HASKELL
PROGRAMMING IN HASKELL
Carlos Varela Rensselaer Polytechnic Institute November 17, 2017
MON TUE WED THU
Types and Classes in Haskell
2008 Calendar.
PROGRAMMING IN HASKELL
CS21 Decidability and Tractability
Sun Mon Tue Wed Thu Fri Sat
CSCE 314: Programming Languages Dr. Dylan Shell
Sun Mon Tue Wed Thu Fri Sat
Curry A Tasty dish? Haskell Curry!.
1/○~1/○ weekly schedule MON TUE WED THU FRI SAT SUN MEMO
2016 | 10 OCT SUN MON TUE WED THU FRI SAT
Sun Mon Tue Wed Thu Fri Sat
Carlos Varela Rennselaer Polytechnic Institute November 15, 2016
2008 Calendar.
Presentation transcript:

Logic Programming (cont’d): Lists Lists in Prolog are represented by a functor (similar to cons in Scheme): 1.The empty list is represented by the constant - [ ]. 2.The term.(X, Xs) represents a list of which X is the 1 st element and Xs is the rest of its elements. 3.The functor ‘. ’ has an infix representation by the pipe symbol ‘|’ : [X | Xs] For example: [3 | [5 | [] ] ] 4.Lists of known length can be represented as a list of comma-separated expressions: For example: [ X, 2, f(Y) ] or [3, 5]

Logic Programming (cont’d): Lists Example 1: Implementing a Context Free Grammar in PROLOG: NP VP Det N V NP | V a | the woman | man saw S NP VP Det N V Q: What language does this CFG represent? s(Z) :- np(X),vp(Y),append(X,Y,Z). np(Z):- det(X),n(Y),append(X,Y,Z). vp(Z):- v(X),np(Y),append(X,Y,Z). vp(Z):- v(Z). det([the]). det([a]). n([woman]). n([man]). v([saw]). s(Z) :- np(X),vp(Y),append(X,Y,Z). np(Z):- det(X),n(Y),append(X,Y,Z). vp(Z):- v(X),np(Y),append(X,Y,Z). vp(Z):- v(Z). det([the]). det([a]). n([woman]). n([man]). v([saw]). Representation in PROLOG: ?- s([a,woman,saw,a,man]). true ?-s(X). X = [the,woman,saw,the,woman]; X = [the,woman,saw,the,man]; X = [the,woman,saw,a,woman]; X = [the,woman,saw,a,man]; X = [the,woman,saw] … ?-s([the,man|X]). X = [saw,the,woman]; X = [saw,the,man]; X = [saw,a,woman] …

Logic Programming (cont’d): Lists Example 1: Implementing a Context Free Grammar in PROLOG: NP VP Det N | Det Adj N vicious | marvelous V NP | V a | the woman | man saw S NP Adj VP Det N V Representation in PROLOG: Q: How would we implement the modifications above? s(Z) :- np(X),vp(Y),append(X,Y,Z). np(Z):- det(X),n(Y),append(X,Y,Z). vp(Z):- v(X),np(Y),append(X,Y,Z). vp(Z):- v(Z). det([the]). det([a]). n([woman]). n([man]). v([shoots]). s(Z) :- np(X),vp(Y),append(X,Y,Z). np(Z):- det(X),n(Y),append(X,Y,Z). vp(Z):- v(X),np(Y),append(X,Y,Z). vp(Z):- v(Z). det([the]). det([a]). n([woman]). n([man]). v([shoots]). s(Z) :- np(X),vp(Y),append(X,Y,Z). np(Z):- det(X),n(Y),append(X,Y,Z). np(Z):- det(X),adj(W),n(Y),append([X,W,Y],Z). adj([vicious]). adj([marvelous]). vp(Z):- v(X),np(Y),append(X,Y,Z). vp(Z):- v(Z). det([the]). det([a]). n([woman]). n([man]). v([shoots]). s(Z) :- np(X),vp(Y),append(X,Y,Z). np(Z):- det(X),n(Y),append(X,Y,Z). np(Z):- det(X),adj(W),n(Y),append([X,W,Y],Z). adj([vicious]). adj([marvelous]). vp(Z):- v(X),np(Y),append(X,Y,Z). vp(Z):- v(Z). det([the]). det([a]). n([woman]). n([man]). v([shoots]).

Logic Programming (cont’d): Lists Example 2: Determining the order of specific times o In logic programming, symbols have no values: ‘2’ and ‘9’ are names and not numbers. o We cannot use the < relation to compare the order of numbers (it is infinite!). o However, a finite ordered relation may be represented by positions in lists. We would like to implement an ordered relation between pairs of the form (hour, weekday). % Type: Hour. % Signature: h(Hour)/1 % Example: h(18). % Type: Hour. % Signature: h(Hour)/1 % Example: h(18). % Type: Weekday. % Signature: d(Weekday)/1 % Example: d(Tue). % Type: Weekday. % Signature: d(Weekday)/1 % Example: d(Tue).

Logic Programming (cont’d): Lists Example 2: Determining the order of specific times o In logic programming, symbols have no values: ‘2’ and ‘9’ are names and not numbers. o We cannot use the < relation to compare the order of numbers (it is infinite!). o However, a finite ordered relation may be represented by positions in lists. We would like to implement an ordered relation between pairs of the form (hour, weekday). % Signature: weekday_list(List)/1 % Purpose: Holds the ordered list of week days. weekday_list([d('Sun'),d('Mon'),d('Tue'),d('Wed'),d('Thu'),d('Fri'),d('Sat')]). % Signature: weekday_list(List)/1 % Purpose: Holds the ordered list of week days. weekday_list([d('Sun'),d('Mon'),d('Tue'),d('Wed'),d('Thu'),d('Fri'),d('Sat')]). % Signature: hour_list(List)/1 % Purpose: Holds the ordered list of days hours. hour_list([h(0),h(1),h(2),h(3),h(4),h(5),h(6),h(7),h(8),h(9),h(10),h(11),h(12), h(13),h(14),h(15),h(16),h(17),h(18),h(19),h(20),h(21),h(22),h(23)]). % Signature: hour_list(List)/1 % Purpose: Holds the ordered list of days hours. hour_list([h(0),h(1),h(2),h(3),h(4),h(5),h(6),h(7),h(8),h(9),h(10),h(11),h(12), h(13),h(14),h(15),h(16),h(17),h(18),h(19),h(20),h(21),h(22),h(23)]).

Logic Programming (cont’d): Lists Example 2: Determining the order of specific times weekday_list([d('Sun'),d('Mon'),d('Tue'),d('Wed'),d('Thu'),d('Fri'),d('Sat')]). hour_list([h(0),h(1),h(2),h(3),h(4),h(5),h(6),h(7),h(8),h(9),h(10),h(11),h(12), h(13),h(14),h(15),h(16),h(17),h(18),h(19),h(20),h(21),h(22),h(23)]). % Signature: is_hour?(Hour)/1 % Purpose: Succeeds iff Hour is an hour of the weekday. is_hour(h(H)) :- hour_list(Hour_list), member(h(H),Hour_list). % Signature: is_hour?(Hour)/1 % Purpose: Succeeds iff Hour is an hour of the weekday. is_hour(h(H)) :- hour_list(Hour_list), member(h(H),Hour_list). A predicate to identify hours: % Signature: hour_order(H1,H2)/2 % Purpose: hour H1 precedes the hour H2 in some weekday. hour_order(h(H1),h(H2)) :- is_hour(h(H1)), is_hour(h(H2)), hour_list(Hour_list), precedes(h(H1),h(H2),Hour_list). % Signature: hour_order(H1,H2)/2 % Purpose: hour H1 precedes the hour H2 in some weekday. hour_order(h(H1),h(H2)) :- is_hour(h(H1)), is_hour(h(H2)), hour_list(Hour_list), precedes(h(H1),h(H2),Hour_list). An order relation between hours:

Logic Programming (cont’d): Lists Example 2: Determining the order of specific times % Signature: is_weekday?(Day)/1 % Purpose: Success iff Weekday is a weekday of the week. is_weekday?(d(D)) :- weekday_list(Weekday_list), member(d(D),Weekday_list). % Signature: is_weekday?(Day)/1 % Purpose: Success iff Weekday is a weekday of the week. is_weekday?(d(D)) :- weekday_list(Weekday_list), member(d(D),Weekday_list). A predicate to identify weekdays: % Signature: weekday_order(Weekday1,Weekday2)/2 % Purpose: Weekday1 precedes weekday2 % in some week. weekday_LT(d(D1),d(D2)) :- is_weekday(d(D1)), is_weekday(d(D2)), weekday_list(Weekday_list), precedes(d(D1),d(D2),Weekday_list). % Signature: weekday_order(Weekday1,Weekday2)/2 % Purpose: Weekday1 precedes weekday2 % in some week. weekday_LT(d(D1),d(D2)) :- is_weekday(d(D1)), is_weekday(d(D2)), weekday_list(Weekday_list), precedes(d(D1),d(D2),Weekday_list). An order relation between weekdays: weekday_list([d('Sun'),d('Mon'),d('Tue'),d('Wed'),d('Thu'),d('Fri'),d('Sat')]). hour_list([h(0),h(1),h(2),h(3),h(4),h(5),h(6),h(7),h(8),h(9),h(10),h(11),h(12), h(13),h(14),h(15),h(16),h(17),h(18),h(19),h(20),h(21),h(22),h(23)]).

Logic Programming (cont’d): Lists Example 2: Determining the order of specific times % Signature: time_LT(T1,T2)/2 % Purpose: The time T1 precedes the time T2 in the week. % Example: ?- time_order(time(h(5),d(‘Mon’)), time(h(1),d(‘Tue’)). % true. time_order(time(h(H1),d(D1)),time(h(H2),d(D2))) :- is_time(time(h(H1),d(D1))), is_time(time(h(H2),d(D2))), weekday_order(d(D1),d(D2)). time_order(time(h(H1),d(D)),time(h(H2),d(D))) :- is_time(time(h(H1),d(D))), is_time(time(h(H2),d(D))), hour_order(h(H1),h(H2)). % Signature: time_LT(T1,T2)/2 % Purpose: The time T1 precedes the time T2 in the week. % Example: ?- time_order(time(h(5),d(‘Mon’)), time(h(1),d(‘Tue’)). % true. time_order(time(h(H1),d(D1)),time(h(H2),d(D2))) :- is_time(time(h(H1),d(D1))), is_time(time(h(H2),d(D2))), weekday_order(d(D1),d(D2)). time_order(time(h(H1),d(D)),time(h(H2),d(D))) :- is_time(time(h(H1),d(D))), is_time(time(h(H2),d(D))), hour_order(h(H1),h(H2)). An order relation between times: % Signature: is_time?(Time)/1 % Purpose: Succeeds iff Time is an hour of some weekday. % Example: ? – is_time? (time(h(1),d(‘Sun’))). true. is_time?(time(h(H),d(D))) :- is_hour?(h(H)), is_weekday?(d(D)). % Signature: is_time?(Time)/1 % Purpose: Succeeds iff Time is an hour of some weekday. % Example: ? – is_time? (time(h(1),d(‘Sun’))). true. is_time?(time(h(H),d(D))) :- is_hour?(h(H)), is_weekday?(d(D)). A predicate to identify times: % Type: Time. % Signature: time(Hour,WeekDay)/2 % Example: time(h(18),d(Tue)). % Type: Time. % Signature: time(Hour,WeekDay)/2 % Example: time(h(18),d(Tue)).

Logic Programming (cont’d): Lists Example 3: Deleting one occurrence of an element from a list. % Signature: select(X,HasXs,OneLessXs)/3 % Purpose: The list OneLessXs is the result of removing % one occurrence of X from the list HasXs. select(Element, HasXs, OneLessXs) :- append([Prefix, [Element], Suffix], HasXs), append(Prefix, Suffix, OneLessXs). % Signature: select(X,HasXs,OneLessXs)/3 % Purpose: The list OneLessXs is the result of removing % one occurrence of X from the list HasXs. select(Element, HasXs, OneLessXs) :- append([Prefix, [Element], Suffix], HasXs), append(Prefix, Suffix, OneLessXs). ?- select(4,[2,3,2,4,5,2,4],X). X = [2, 3, 2, 5, 2, 4]; X = [2, 3, 2, 4, 5, 2]; false

Logic Programming (cont’d): Lists Example 4: Merging sorted lists % Signature: merge(Xs,Ys,Zs)/3 % Purpose: Zs is the sorted merge of the sorted lists Xs and Ys. Assumes % there a predicate "lt" of order between elements of Xs and Ys. merge([X|Xs],[Y|Ys],[X|Zs]) :- lt(X,Y), merge(Xs,[Y|Ys],Zs).%1 merge([X|Xs],[X|Ys],[X,X|Zs]) :- merge(Xs,Ys,Zs).%2 merge([X|Xs],[Y|Ys],[Y|Zs]) :- lt(Y,X), merge([X|Xs],Ys,Zs).%3 merge(Xs,[],Xs).%4 merge([],Ys,Ys).%5 % Signature: merge(Xs,Ys,Zs)/3 % Purpose: Zs is the sorted merge of the sorted lists Xs and Ys. Assumes % there a predicate "lt" of order between elements of Xs and Ys. merge([X|Xs],[Y|Ys],[X|Zs]) :- lt(X,Y), merge(Xs,[Y|Ys],Zs).%1 merge([X|Xs],[X|Ys],[X,X|Zs]) :- merge(Xs,Ys,Zs).%2 merge([X|Xs],[Y|Ys],[Y|Zs]) :- lt(Y,X), merge([X|Xs],Ys,Zs).%3 merge(Xs,[],Xs).%4 merge([],Ys,Ys).%5 ?- merge([time(h(5),d('Sun')),time(h(5),d('Mon'))], X, [time(h(2),d('Sun')),time(h(5),d('Sun')),time(h(5),d('Mon'))]). X = [time(h(2),d( 'Sun'))] % Signature: lt(Obj1,Obj2)/2 % Purpose: Obj1 precedes Obj2 by some comparison criteria. lt(Time1,Time2) :- time_LT(Time1,Time2). % Signature: lt(Obj1,Obj2)/2 % Purpose: Obj1 precedes Obj2 by some comparison criteria. lt(Time1,Time2) :- time_LT(Time1,Time2).

Logic Programming (cont’d): Lists Example 5: Merging sorted lists merge([t1,t3,t5],[t2,t3],Xs) { X_1=t1,Xs_1=[t3,t5], Y_1=t2,Ys_1=[t3], Xs=[t1|Zs_1] } 1 merge([t3,t5],[t2,t3],Zs_1) 2 – failure branch… 1 – failure branch… { X_3=t3,Xs_3=[t5],Y_3=t3,Ys_3=[],Zs_2=[t3,t3|Zs_3] } 2 merge([t3,t5],[t3],Zs_2) 1 – failure branch… merge([t5],[],Zs_3) true { Xs_4=[t5],Ys_4=[], Zs_3=[t5] } 4 merge([X|Xs],[Y|Ys],[X|Zs]) :- lt(X,Y), merge(Xs,[Y|Ys],Zs). merge([X|Xs],[X|Ys],[X,X|Zs]) :- merge(Xs,Ys,Zs). merge([X|Xs],[Y|Ys],[Y|Zs]) :- lt(Y,X), merge([X|Xs],Ys,Zs). merge(Xs,[],Xs). merge([],Ys,Ys). merge([X|Xs],[Y|Ys],[X|Zs]) :- lt(X,Y), merge(Xs,[Y|Ys],Zs). merge([X|Xs],[X|Ys],[X,X|Zs]) :- merge(Xs,Ys,Zs). merge([X|Xs],[Y|Ys],[Y|Zs]) :- lt(Y,X), merge([X|Xs],Ys,Zs). merge(Xs,[],Xs). merge([],Ys,Ys). ?-merge( [ time(h(1),d('Sun')), time(h(3),d('Wed')), time(h(5), d('Sat'))], [ time(h(2), d('Sun')), time(h(3),d('Wed'))], Xs) lt(t1,t2), merge([t3,t5],[t2,t3],Zs_1) * lt(t2,t3), merge([t3,t5],[t3],Zs_2) * 1 – failure branch… { X_2=t3,Xs_2=[t5], Y_2=t2, Ys_2=[t3], Zs_1=[t2|Zs_2] } 3 2 – failure branch… 3 – failure branch…

Logic Programming (cont’d): Backtracking optimization merge([t1,t3,t5],[t2,t3],Xs) !, merge([t3,t5],[t2,t3],Zs_1) merge([X|Xs],[Y|Ys],[X|Zs]) :- lt(X,Y), !, merge(Xs,[Y|Ys],Zs). merge([X|Xs],[X|Ys],[X,X|Zs]) :- merge(Xs,Ys,Zs). merge([X|Xs],[Y|Ys],[Y|Zs]) :- lt(Y,X), merge([X|Xs],Ys,Zs). merge([X|Xs],[Y|Ys],[X|Zs]) :- lt(X,Y), !, merge(Xs,[Y|Ys],Zs). merge([X|Xs],[X|Ys],[X,X|Zs]) :- merge(Xs,Ys,Zs). merge([X|Xs],[Y|Ys],[Y|Zs]) :- lt(Y,X), merge([X|Xs],Ys,Zs). lt(t1,t2), !, merge([t3,t5],[t2,t3],Zs_1) Example 7: Optimize the procedure merge. o When none of the first two params is [], only one of the rules can be valid, o Since either lt(Y,X), or lt(X,Y) or X==Y holds, exclusively. o Once one of the above holds, we can skip further rule selections. merge([t3,t5],[t2,t3],Zs_1) 3 – failure branch… 2 – failure branch…

Logic Programming (cont’d): Backtracking optimization Rule k:A :- B 1, …B i, !, B i+1, …, B n. Rule k+1:A :- …. … ?- B 1,…, B i, !, B i+1, …B n,Q 1 ’,…Q m ’ Rule k * ?- !, B i+1 ’, …B n ’,Q 1 ’’,…Q n ’’ ?- B i+1 ’, …B n ’,Q 1 ’’,…Q n ’’ … Following selections of A rules are cut. Further substitutions for goals before ‘!’ are cut. The cut operator (!): Used to avoid redundant computations.

Logic Programming (cont’d): Backtracking optimization Example 8: red VS green cuts. o Green cut: Helps optimizing the program by avoiding redundant computations. o Red cut: Omits possible solutions. o Red cuts are undesired, unless specifically required (E.g., to provide only the first solution). Q: How many possible solutions does the following query have? ?- merge([],[],X). X = []; X = [] The query matches both facts 4 and 5: merge(Xs,[],Xs). merge([],Ys,Ys). merge(Xs,[],Xs). merge([],Ys,Ys). To avoid this, we add ‘!’ to fact 4, rewriting it as a rule: merge(Xs,[],Xs):- !. merge([],Ys,Ys). merge(Xs,[],Xs):- !. merge([],Ys,Ys). A red cut! The number of solutions has changed!

Logic Programming (cont’d): Meta circular interpreter Recall the second version of the meta-circular interpreter (seen in class): o Based on goals reduction, with explicit control of selection order (using a stack of goals). o Operates in two phases: 1.Preprocessing: The given program, P, is translated into a new program P’, which has a single predicate, rule, and consists of facts only. 2.Queries are applied to the new program using the procedure solve.

Logic Programming (cont’d): Meta circular interpreter member(X,[X|Xs]). member(X,[Y|Ys]) :- member(X,Ys). member(X,[X|Xs]). member(X,[Y|Ys]) :- member(X,Ys). % Signature: rule(Head,BodyList)/2 rule(member(X,[X|Xs]),[]). rule(member(X,[Y|Ys]),[member(X,Ys)]). % Signature: rule(Head,BodyList)/2 rule(member(X,[X|Xs]),[]). rule(member(X,[Y|Ys]),[member(X,Ys)]). Example 10: Applying the meta circular interpreter. Preprocessing % Signature: solve(Goal)/1 % Purpose: Goal is true if it is true when posed to the original program P. % Precondition: rule/2 is defined for the program. solve(Goal) :- solve(Goal,[]). % Signature: solve(Goal,Rest_of_goals)/2 solve([],[]). % (Nothing to prove, empty stack - done). solve([],[G | Goals]) :- solve(G,Goals). % (Nothing to prove, non-empty stack - pop). solve([A|B],Goals) :- append(B,Goals,Goals1), solve(A,Goals1). % (List to prove – push cdr). solve(A,Goals) :- rule(A,B), solve(B,Goals). % Signature: solve(Goal)/1 % Purpose: Goal is true if it is true when posed to the original program P. % Precondition: rule/2 is defined for the program. solve(Goal) :- solve(Goal,[]). % Signature: solve(Goal,Rest_of_goals)/2 solve([],[]). % (Nothing to prove, empty stack - done). solve([],[G | Goals]) :- solve(G,Goals). % (Nothing to prove, non-empty stack - pop). solve([A|B],Goals) :- append(B,Goals,Goals1), solve(A,Goals1). % (List to prove – push cdr). solve(A,Goals) :- rule(A,B), solve(B,Goals).

… {X_3 = X, Y_3 = a, Ys_3 = [b, c], B_2 = [member(X, [b, c])]} Rule 2 rule {A_4 = member(X, [b, c]), B_4 = [], Goals_4 = []} 3 {Goals1_4 = []} Rule of append {A_5 = member(X, [b, c]), Goals_5 = []} 4 {X = b, X_6 = b, Xs_6 = [c], B_5 = []} 1 {Goal_1 = member(X, [a, b, c])} 1 solve(member(X, [a, b, c])) solve(member(X, [a, b, c]), []) {A_2 = member(X, [a, b, c], Goals_1 = []} 4 rule(member(X, [a, b, c], B_2), solve(B_2, [] ) solve([],[]) {X = a, X_3 = a, Xs_3 = [b, c], B_2 = []} 1 true {X = a} 1 solve( [member(X, [b, c])], [] ) append([], [], Goals1_4), solve(member(X, [b, c]), Goals1_4) solve(member(X, [b, c]), []) rule(member(X,[b, c]), B_5), solve(B_5, []) solve([],[]) true {X = b} 1