Download Presentation
## Logic Programming

- - - - - - - - - - - - - - - - - - - - - - - - - - - E N D - - - - - - - - - - - - - - - - - - - - - - - - - - -

**Logic Programming**• Logic-based • Adopt the syntax from logic for both data and programs • A logic variable is a symbol for an object in a domain • Use resolution to infer new propositions from given ones • Declarative: state what should be done rather than how • Language features of Prolog • A program consists of relations defined by facts and rules • Pattern matching • Recursion • Nondeterminism realized through backtracking by Neng-Fa Zhou**A Brief History**• Robinson’s resolution theorem prover (65) • Colmerauer’s NLP project and Q system (early 70’s) • Kowalski’s Horn clauses and SLD resolution (early 70’s) • D.H.D. Warren’s work in the implementation (late 70’s) • Japanese Fifth Generation Project and follow-up projects in Europe and USA (early 80’s) • Constraint logic programming (late 80’s) by Neng-Fa Zhou**Syntax of Prolog**• Term • Atom • string of letters, digits, and '_' starting with a low-case letter • string of characters enclosed in quotes • Number • integer & real • Variable • string of letters, digits and '_' starting with a capital letter or '_' by Neng-Fa Zhou**Syntax of Prolog (Cont)**• Structure • f(t1,t2,...,tn) • f is an atom, called the functor of the structure • t1,t2,...,tn are terms • List • '.'(H,T) => [H|T] • '.'(1,'.'(2,'.'(3,[]))) => [1,2,3] by Neng-Fa Zhou**Syntax of Prolog (Cont)**• Clause • Fact • p(t1,t2,...,tn) • Rule • H :- B1,B2,...,Bm. • Predicate • a sequence of clauses • Program • a set of predicates • Query Head Body by Neng-Fa Zhou**Syntax: Examples**• Facts • Rules • Queries father(terach,abraham).male(terach). parent(Parent,Child):-father(Parent,Child). parent(Parent,Child):-mother(Parent,Child). uncle(Uncle,Person) :- brother(Uncle,Parent), parent(Parent,Person). ?-parent(Parent,abraham). by Neng-Fa Zhou**Unification**• t1 = t2 succeeds if • t1 and t2 are identical • there exists a substitution q for the variables in t1 and t2 such that t1q = t2q. f(X,b)=f(a,Y). X=a Y=b q = {X/a, Y/b} by Neng-Fa Zhou**Unification: Examples**assignment test test matching unification without occur checking ?-X=1. X=1 ?- f(a,b)=f(a,b). yes ?- a=b. no ?- f(X,Y)=f(a,b) X=a Y=b ?-f(X,b)=f(a,Y). X=a Y=b ?-X = f(X). X=f(f(...... by Neng-Fa Zhou**Unification**• unify(t1,t2) • if t1 is a variable, then bind t1 to t2 • if t2 is a variable, then bind t2 to t1 • if t1 and t2 are both atomic values • if t1 and t2 are identical return true • otherwise, return false • t1=f(a1,...,an) and t2=g(b1,...,bm) • if f != g || m != n return false • return unify(a1,b1) && ... && unify(an,bm) by Neng-Fa Zhou**Operational Semantics of Prolog (Resolution)**• G0: initial query • Gi: (A1,A2,...,An) • H:-B1,...,Bm • A1q=H1q • Gi+1: (B1,...,Bm,A2,...,An)q Succeed if Gk is empty for some k.Backtrack if Gk is a dead end (no clause can be used). by Neng-Fa Zhou**Deductive Database**parent(Parent,Child):-father(Parent,Child). parent(Parent,Child):-mother(Parent,Child). uncle(Uncle,Person) :- brother(Uncle,Parent), parent(Parent,Person). sibling(Sib1,Sib2) :- parent(Parent,Sib1), parent(Parent,Sib2), Sib1 \= Sib2. cousin(Cousin1,Cousin2) :- parent(Parent1,Cousin1), parent(Parent2,Cousin2), sibling(Parent1,Parent2). by Neng-Fa Zhou**Exercise**• Will the following unification operations succeed or fail? If they succeed, what are the substitutions? • point(A,B) = point(1,2) • point(A,B) = point(X,Y,Z) • plus(2,2) = 4 • +(2,D) = +(E,2) • tri(point(-1,0),P2,P3) = tri(P1,point(1,0),point(0,Y)) by Neng-Fa Zhou**Exercise**• Define the following relations • son(X,Y) -- X is a son of Y • daughter(X,Y) -- X is a daughter of Y • grandfather(X,Y) -- X is the grandfather of Y • grandparent(X,Y) -- X is a grandparent of Y • ancestor(X,Y) – X is an ancestor of Y by Neng-Fa Zhou**Built-ins in Prolog**• Unification • T1 = T2 • T1 \= T2 • Arithmetic • X is Exp • Exp =:= Exp, Exp =\= Exp • Exp >= Exp, Exp > Exp • Exp =< Exp, Exp < X can be a variable or a ground expression Exp must be a groundexpression by Neng-Fa Zhou**Examples(=, \=, is, =:=, =\=, >, >=, <, =<)**by Neng-Fa Zhou**Built-ins in Prolog (cont.)**• arg(N,T,A) • The Nth argument of T is A • functor(T,F,N) • the functor of T is F/N. • T1==T2 • T1 and T2 are identical • T1 \== T2 • T1 and T2 are not identical by Neng-Fa Zhou**Examples(arg, functor, ==, \==)**by Neng-Fa Zhou**Recursive Programming**• Recursively defined data structures • S-expressions • 0, s(0), s(s(0)), … • Lists • [], [X|L] • Binary trees • void, t(N,L,R) by Neng-Fa Zhou**Recursive Programming on S-Expressions**• Definition of S-Expressions • 0, s(0), s(s(0)),.... • sum(X,Y,Z) -- X+Y makes Z • prod(X,Y,Z) -- X*Y makes Z sum(0,Y,Y). sum(s(X),Y,s(Z)):-sum(X,Y,Z). prod(0,Y,0). prod(s(X),Y,Z):- prod(X,Y,Z1), sum(Z1,Y,Z). by Neng-Fa Zhou**Recursive Programming on S-Expressions (Cont.)**• Conversion of integers to s-expressions int2s(0,0). int2s(N,s(S)):- N>0, N1 is N-1, int2s(N1,S). by Neng-Fa Zhou**Exercise**• Define the following arithmetic operations on natural numbers. • power(X,Y,Z) XY=Z • factorial(X,Y) X!=Y • lt(X,Y) X is less than Y • one_hundred(X) X = 100 (s(s(....(s(0)))...) • sum_1_to_100(X) X = 1+2+...+100 by Neng-Fa Zhou**Recursive Programming on Lists**• A list is a special structure whose functor is '.'/2 • [] • '.'(H,T) => [H|T] • '.'(1,'.'(2,'.'(3,[]))) => [1,2,3] • Unification of lists • [X|Xs]=[1,2,3] X= 1 Xs=[2,3] • [1,2,3] = [1|[2|X]] X=[3] • [1,2|3] = [1|X] X=[2|3] by Neng-Fa Zhou**Relations on Lists**• isList(Xs) • member(X,Xs) • append(Xs,Ys,Zs) • length(Xs,N) isList([]). isList([X|Xs]):-isList(Xs). member(X,[X|Xs]). member(X,[_|Xs]):-member(X,Xs). append([],Ys,Ys). append([X|Xs],Ys,[X|Zs]):-append(Xs,Ys,Zs). length([],0). length([X|Xs],N):-length(Xs,N1),N is N1+1. by Neng-Fa Zhou**Implement the following predicates.**length(Xs,N) the length of Xs is N last(X,Xs) X is the last element of Xs. prefix(Pre,Xs) Pre is a prefix of Xs. suffix(Pos,Xs) suffix is a postfix of Xs reverse(Xs,Ys) Ys is the reverse of Xs sum(Xs,N) N is the sum of the integers in the list Xs sum1(Xs,Ys) assume Xs is [x1,x2,...,xn], then Ys will be [y1,y2,...,yn] where yi is xi+1. sort(L,SortedL) use the exchange sort algorithm Exercise by Neng-Fa Zhou**Recursive Programming on Binary Trees**• Representation of binary trees • Example void -- empty tree t(N, L,R) -- N : node L : Left child R : Right child a t(a, t(b, void,void), t(c,void,void)) c b by Neng-Fa Zhou**Relations on Binary Trees**• isBinaryTree(T)-- T is a binary tree • count(T,C) -- C is the number of nodes in T. isBinaryTree(void). isBinaryTree(t(N,L,R)):- isBinaryTree(L), isBinaryTree(R). count(void,0). count(t(N,L,R),N):- count(L,N1), count(R,N2), N is N1+N2+1. by Neng-Fa Zhou**Relations on Binary Trees (Cont.)**• preorder(T,L) • L is a pre-order traversal of the binary tree T. preorder(void,[]). preorder(t(N,Left,Right),L):- preorder(Left,L1), preorder(Right,L2), append([N|L1],L2,L). by Neng-Fa Zhou**Exercise**• Write the following predicates on binary trees. • leaves(T,L): L is the list of leaves in T. The order is preserved. • equal(T1,T2): T1 and T2 are the same tree. • postorder(T,L): L is the post-order traversal of T. by Neng-Fa Zhou**Tail Recursive Programs and Difference Lists**• Recursion is slower and consumes more space than iteration. • Prolog compilers performs Tail-Recursion-Optimization, which converts tail recursion into iteration. • In general, tail-recursive programs are more efficient than non-tail-recursive programs. by Neng-Fa Zhou**Tail-Recursive PredicatesExample: product**prod(0,Y,0). prod(s(X),Y,Z):- prod(X,Y,Z1), sum(Z1,Y,Z). Accumulator prod(X,Y,Z):- prod(X,Y,0,Z). prod(0,Y,Z,Z). prod(s(X),Y,Z0,Z):- sum(Y,Z0,Z1), prod(X,Y,Z1,Z). by Neng-Fa Zhou**Example: length**length([],0). length([X|Xs],N):- length(Xs,N1), N is N1+1. length(Xs,N):- length(Xs,0,N). length([],N,N). length([X|Xs],N0,N):- N1 is N0+1, length(Xs,N1,N). by Neng-Fa Zhou**Example: reverse**reverse([],[]). reverse([X|Xs],Zs):- reverse(Xs,Ys), append(Ys,[X],Zs). reverse(Xs,Ys):- reverse(Xs,[],Ys). reverse([],Ys,Ys). reverse([X|Xs],Ys0,Ys):- reverse(Xs,[X|Ys0],Ys). by Neng-Fa Zhou**Example: count**count(void,0). count(t(N,L,R),N):- count(L,N1), count(R,N2), N is N1+N2+1. count(T,N):- count(T,0,N). count(void,N,N). count(t(N,L,R),N0,N):- N1 is N0+1, count(L,N1,N2), count(R,N2,N). by Neng-Fa Zhou**Difference Lists**leaves(void,[]). leaves(t(N,void,void),L):-!, L=[N]. leaves(t(N,Left,Right),L):- leaves(Left,L1), leaves(Right,L2), append(L1,L2,L). leaves(T,L):- leaves(T,L,[]). leaves(void,L,L). leaves(t(N,void,void),L,LR):-!,L=[N|LR]. leaves(t(N,Left,Right),L,LR):- leaves(Left,L,L1), leaves(Right,L1,LR). L-[] equals L L-L equals [] L-LR equals (L-L1) + (L1-LR) by Neng-Fa Zhou**Exercises**• Define the following predicates and convert them into tail-recursive ones. • merge(L1,L2,L) • L is the merge of two sorted lists L1 and L2. L must be sorted too. • preorder(T,L) • L is the list of nodes in the binary tree T in pre-order. by Neng-Fa Zhou**Backtracking and Its Control**• For a goal and a program, Prolog constructs and explores the search tree (SLD-tree) through backtracking, i.e., top-down and from left to right. • Prolog provides an operator '!' (called cut) for pruning useless branches. by Neng-Fa Zhou**The Meaning of Backtracking**• Gi: (A1,A2,...,An) • H:-B1,...,Bm • A1q=H1q • Gi+1: (B1,...,Bm,A2,...,An)q • When Gi+1 fails, • undo the bindings of the variables in Gi • apply an alternative clause to A1 • A1 fails if no such a clause is available, which will cause Gi to fail. by Neng-Fa Zhou**BacktrackingExample**p(X) p(a). p(b). p(c). X=a X=b X=c [] [] [] by Neng-Fa Zhou**BacktrackingExample**p(a). q(1). p(b). q(2) p(c). p(X),q(Y) X=b X=a X=c q(Y) q(Y) q(Y) Y=1 Y=2 Y=1 Y=2 Y=1 Y=2 [] [] [] [] [] [] by Neng-Fa Zhou**BacktrackingExample-- member**• Can be used in two different ways • test whether the element is a member of the list • member(b,[a,b,c]) • pickup elements from the list one by one • member(X,[a,b,c]) member(X,[X|Xs]). member(X,[_|Xs]):-member(X,Xs). by Neng-Fa Zhou**BacktrackingExample -- select**• select(Xs,X,Rest) • X is an element in Xs and Rest is Xs but without X. select([X|Xs],X,Xs). select([X|Xs],Y,[X|Xs1]):-select(Xs,Y,Xs1). by Neng-Fa Zhou**BacktrackingExample -- permutation**• permutation(Xs,Ys) • Ys is a permutation of Xs permutation([],[]). permutation(Xs,[X|Ys]):- select(Xs,X,Xs1), permutation(Xs1,Ys). by Neng-Fa Zhou**Exercises**• Define the following predicates • subset(Xs,Ys) • Xs is a subset of Ys. Assume Xs and Ys do not contain duplicates. • intersect(Xs,Ys,Zs) • Zs is the intersect of Xs and Ys. by Neng-Fa Zhou**BacktrackingExample -- permutation sort**• sort(Xs,SortedXs) • SortedXs is Xs sorted in ascending order sort(Xs,SortedXs):- permutation(Xs,SortedXs), %generator sorted(SortedXs). %test sorted([]). sorted([X]). sorted([X1,X2|Xs]):- X1=<X2, sorted([X2|Xs]). by Neng-Fa Zhou**BacktrackingN-queens problem**• Find a layout for the N queens on an N by N chessboard such that no queens attack each other. Two queens attack each other if they are in the same row, the same column, or the same diagonal. Xi: the number of the row for the ith queen. for each two variables Xi and Xj Xi =\= Xj %not same row Xi=\=Xj+(j-i) %not same diagonal Xi=\=Xj-(j-i) by Neng-Fa Zhou**N-queens problem (cont.)**queens(N,Qs):- range(1,N,Ns), permutation(Ns,Qs), notAttack(Qs). range(N0,N,Ns):- N0=:=N,Ns=[N]. range(N0,N,Ns):- N0<N, Ns=[N0|Ns1], N1 is N0+1, range(N1,N,Ns1). notAttack([]). notAttack([X|Xs]):- notAttack(X,Xs,1), notAttack(Xs). notAttack(X,[],K). notAttack(X,[Y|Ys],K):- X=\=Y, X=\=Y+K, X=\=Y-K, K1 is K+1, notAttack(X,Ys,K1). by Neng-Fa Zhou**N-queens problem (cont.)Test partial solutions ASA**queens(N,Qs):- range(1,N,Ns), queens(Ns,[],Qs). queens([],Qs,Qs). queens(Xs,Qs0,Qs):- select(Xs,X,Xs1), notAttack(X,Qs0,1), queens(Xs1,[X|Qs0],Qs). by Neng-Fa Zhou**Exercises**• 1.Write a program to solve the following puzzle. • Given eight letters S,E, N, D, M, O, R and Y, one is required to assign a digit between 0 and 9 to each letter such that all the letters have different values and the equation SEND + MORE = MONEY is satisfied. • 2. Write a program to color the map of Western Europe. The map is given in the following. map(west_europe, [ region(portugal,P,[E]), region(spain,E,[F,P]), region(france,F,[E,I,S,B,WG,L]), region(belgium,B,[F,H,L,WG]), region(holland,H,[B,WG]), region(west_germany,WG,[F,A,S,H,B,L]), region(luxembourg,L,[F,B,WG]), region(italy,I,[F,A,S]), region(switzerland,S,[F,I,A,WG]), region(austria,A,[I,S,WG])]). by Neng-Fa Zhou**Controlling Backtracking**• Use cut to express if-then-else intersect([],Ys,[]). intersect([X|Xs],Ys,[X|Zs]):- member(X,Ys), intersect(Xs,Ys,Zs). intersect([X|Xs],Ys,Zs):- not member(X,Ys), intersect(Xs,Ys,Zs). intersect([],Ys,[]). intersect([X|Xs],Ys,[X|Zs]):- member(X,Ys),!, intersect(Xs,Ys,Zs). intersect([X|Xs],Ys,Zs):- not member(X,Ys), intersect(Xs,Ys,Zs). by Neng-Fa Zhou**Controlling Backtracking (Cont.)**• Use cut to express negation-as-failure not(Call):- call(Call),!, fail. not(Call). by Neng-Fa Zhou