930 likes | 939 Views
An introduction to Logic Programming. Chapter 6. Chapter topics. Introduction Relational Logic Programming : specify relations among entities Logic Programming : data structures: lists, binary trees, symbolic expressions, natural numbers (church) Prolog : arithmetic , cuts, negation
E N D
An introduction to Logic Programming Chapter 6
Chapter topics • Introduction • Relational Logic Programming: specify relations among entities • Logic Programming: data structures: lists, binary trees, symbolic expressions, natural numbers (church) • Prolog: arithmetic, cuts, negation • Meta-circular Interpreters for Logic Programming
Logic Programming: Introduction • Origin: automate the process of proving logical statements • Mind switch: • Formula ⇔ procedure declaration • Query ⇔procedure call • Proving ⇔ computation
Logic Programming: Introduction Every programming language has: • Syntax: set of formulas (facts and rules) • Semantics (set of answers) • Operational Semantics (how to get an answer): • Unification • Backtracking
Logic Programming: Introduction • The building blocks of LP expressions are formulas: formulas defined relations. For example, formula p(X,Y) - a relation between X and Y called p. • axioms - are the knowledge base. axioms have the form: X1,X2,...,XkH B1 and B2 ... and Bn • A query - claim that the computation is attempting to proof. A query has the form X1,X2,...,Xk Q1 and Q2 ... and Qm A typical logic programming answer "X1=..., ... Xk=... also X1 =..., ... Xk=... " • Operational semantics: set of axioms procedure definitionquery procedure application interpretation prove query via program
Logic programming model Kowalski's interpretation: An axiom H B1 and B2 ... and Bnrepresents a procedure • H is the procedure’s head and the Bi’s are its body • To solve (execute) H, we recursively solve B1 ... Bn
Relational LP • a computational model based on Kowalski's interpretation • The Prolog language ('70) - contains RLP + additional programming features
Relational LP - Syntax • atomic formula: predicate_symbol(term1, ..., termn) • predicate symbols start with lowercase • terms: • symbols (representing individual constants) • variables (start with uppercase or _ for anonymous)
Relational LP - Semantics • Values: • all atomic values are symbols (typeless) • Very few primitive predicates, such as = (unification), \=, true, false • Computation output: • an answer to a query. • An answer to a query is a (possibly partial) substitution (assignment) of query variables.
Relational LP Syntax - formulas • atomic formula: Syntax: predicate_symbol(term1,...,termn) Examples: male(moshe) color(red) parent(reuven, moshe) parent(moshe, rina) parent(Parent, Child) ancestor(A,D) address(_City, hertzel, 20) • The only difference between predicates and individual constant symbols are their context/location.
Relational LP Syntax - Procedures • A fact is an assertion of an atomic formula. Syntax: H. where H is an atomic formula. Examples: parent(rina, moshe). color(red). ancestor(A,A). • Variables in facts are universally quantified. "for all A, it holds that ancestor(A,A)". • Procedures are an ordered collection of axioms (facts and rules)sharing the same predicate name and arity.
% Signature: parent(Parent, Child)/2 % Purpose: Parent is a parent of Child parent(rina, moshe). parent(rina, rachel). parent(rachel, yossi). parent(reuven, moshe). % Signature: female(Person)/1 % Purpose: Person is a female. female(rina). female(rachel). • Predicates have arity(no. of parameters). specified in /n in the comment above the procedure. • not necessarily unique
Relational LP Syntax - Queries A query has the syntax: ?- Q1, Q2, . . . , Qn. where the Qi are atomic formulas. Meaning: Assuming the program axioms, do Q1 and ... and Qn hold? ',' means conjunction. For example, ?- parent(rina, moshe). "Is rina a parent of moshe?” A computation is a proof of a query, returns: true ; false. user requests another answer
Relational LP Syntax - Queries A query has the syntax: ?- Q1, Q2, . . . , Qn. where the Qi are atomic formulas. Meaning: Assuming the program axioms, do Q1 and ... and Qn hold as well? ',' means conjunction. For example, ?- parent(rina,X). "Does there exist an X which is a child of rina?" X = moshe ; X = rachel. • Variables in queries are existentially quantified.
Relational LP Syntax - Queries "Is there an X which is a child of rina, and is also a parent of some Y?" ?- parent(rina,X),parent(X,Y). X = rachel, Y = yossi. "Find two parents of moshe?": ?- parent(X,moshe),parent(Y,moshe). X = rina, Y = rina ; X = rina, Y = reuven ; X = reuven, Y = rina ; X = reuven, Y = reuven.
Relational LP Syntax - Queries "Find two different parents of moshe?": ?- parent(X,moshe),parent(Y,moshe),X \= Y. X = rina, Y = reuven ; X = reuven, Y = rina ; false. ?- parent(X,moshe), X \= Y, parent(Y,moshe). false. ?- X=3. X = 3. ?- X\=3. false. ?- 4\=3. true.
Relational LP - Syntax % Signature: loves(Someone, Somebody)/2 % Purpose: Someone loves Somebody loves(rina,Y). % rina loves everybody. loves(moshe, rachel). loves(moshe, rina). loves(Y,Y). % everybody loves himself • Variables in axioms are universally quantified. "for all Y loves(rina,Y)" can be renamed "for all X loves(rina,X)" • Using a variable in a fact is defining it. The scope is the fact itself.
Relational LP - Syntax % Signature: loves(Someone, Somebody)/2 % Purpose: Someone loves Somebody loves(rina,Y). % rina loves everybody. loves(moshe, rachel). loves(moshe, rina). loves(Y,Y). % everybody loves himself Queries: ?- loves(rina,moshe). true ; false.
Relational LP - Syntax % Signature: loves(Someone, Somebody)/2 % Purpose: Someone loves Somebody loves(rina,Y). % rina loves everybody. loves(moshe, rachel). loves(moshe, rina). loves(Y,Y). % everybody loves himself Queries: ?- loves(rina,X). true ; X = rina.
Relational LP - Syntax % Signature: loves(Someone, Somebody)/2 % Purpose: Someone loves Somebody loves(rina,Y). % rina loves everybody. loves(moshe, rachel). loves(moshe, rina). loves(Y,Y). % everybody loves himself Queries: ?- loves(X,rina). X = rina ; X = moshe ; X = rina.
Relational LP - Syntax % Signature: loves(Someone, Somebody)/2 % Purpose: Someone loves Somebody loves(rina,Y). % rina loves everybody. loves(moshe, rachel). loves(moshe, rina). loves(Y,Y). % everybody loves himself Queries: ?- loves(X,X). X = rina ; true. this query has two answers.
Relational LP Syntax - Rules • Syntax:H :−B1, . . . , Bn. is an assertion of an implication statement. The conjunction of B1, .., Bn implies the head H. Bi's and H are atomic formulas. % Signature: mother(Mum, Child), % Purpose: Mum is a mother of Child mother(Mum, Child) :- parent(Mum, Child), female(Mum). • Variables occurring in rule heads are universally quantified. The lexical scope of the variable is the rule. • A variable can multiple times in the head. • variables are bound within a rule.
Relational LP Syntax - Rules % Signature: mother(Mum, Child), % Purpose: Mum is a mother of Child mother(Mum, Child) :- parent(Mum, Child), female(Mum). ?- mother(M,C). M = rina, C = moshe ; M = rina, C = rachel ; M = rachel, C = yossi ; false.
Relational LP Syntax - Rules % Signature: mother(Mum, Child), % Purpose: Mum is a mother of Child mother(Mum, Child) :- parent(Mum, Child), female(Mum). “Find a two-different-kids mother” ?- mother(M,C1),mother(M,C2),C1\=C2. M = rina, C1 = moshe, C2 = rachel ; M = rina, C1 = rachel, C2 = moshe ; false.
Relational LP Syntax - Rules the ancestor relationship - a recursive rule that computes the transitive closure of the parent relationship. % Signature: ancestor(Ancestor, Descendant)/2 % Purpose: Ancestor is an ancestor of Descendant. ancestor(Ancestor, Descendant) :- parent(Ancestor, Descendant). ancestor(Ancestor, Descendant) :- parent(Ancestor, Person), ancestor(Person, Descendant). • Variables occurring in the rule body and not in the head are existentially quantified. "for all Ancestor and for all Descendant, ancestor(Ancestor, Descendant) if there exists some Person such that parent(Ancestor, Person) and ancestor(Person, Descendant)."
Relational LP Syntax - Rules the ancestor relationship - a recursive rule that computes the transitive closure of the parent relationship. % Signature: ancestor(Ancestor, Descendant)/2 % Purpose: Ancestor is an ancestor of Descendant. ancestor(Ancestor, Descendant) :- parent(Ancestor, Descendant). ancestor(Ancestor, Descendant) :- parent(Ancestor, Person), ancestor(Person, Descendant). ?- ancestor(rina,D). D = moshe ; D = rachel ; D = yossi ; false.
Relational LP Syntax - Rules the ancestor relationship - a recursive rule that computes the transitive closure of the parent relationship. % Signature: ancestor(Ancestor, Descendant)/2 % Purpose: Ancestor is an ancestor of Descendant. ancestor(Ancestor, Descendant) :- parent(Ancestor, Descendant). ancestor(Ancestor, Descendant) :- parent(Ancestor, Person), ancestor(Person, Descendant). ?- ancestor(A,yossi). A = rachel ; A = rina ; false. • The reported result/functionality depends on the variables and their location in the query.
Relational LP Syntax - Rules ancestor1(Ancestor, Descendant) :- parent(Ancestor, Descendant). ancestor1(Ancestor, Descendant) :- ancestor1(Person, Descendant), parent(Ancestor, Person). ?- ancestor1(A,yossi). A = rachel ; A = rina ; ERROR: Out of local stack ?- ancestor1(rina,yossi). true ; ERROR: Out of local stack • This procedure is not tail recursive. • Since this query cannot be answered using the base case, new similar queries are infinitely created.
Note Facts can be considered as rules with an empty body. For example, parent(rina, moshe). parent(rina, moshe):- true. have equivalent meaning. true - is the zero-arity predicate.
Concrete syntax of Relational Logic Programming <program> -> <procedure>+ <procedure> -> (<rule> | <fact>)+ with identical predicate and arity <rule> -> <head> ’: -’ <body>’.’ <fact> -> <head>’.’ <head> -> <atomic-formula> <body> -> (<atomic-formula>’,’)* <atomic-formula> <atomic-formula> -> <constant> | <predicate>’(’(<term>’,’)* <term>’)’ <predicate> -> <constant> <term> -> <constant> | <variable> <constant> -> A string starting with a lower case letter. <variable> -> A string starting with an upper case letter. <query> -> ’?-’ (<atomic-formula>’,’)* <atomic-formula> ’.’
Summary - RLP Semantic and syntax parent(rina, moshe). parent(rina, rachel). parent(rachel, yossi). parent(reuven, moshe). ancestor(Ancestor, Descendant) :- parent(Ancestor, Descendant). ancestor(Ancestor, Descendant) :- parent(Ancestor, Person), ancestor(Person, Descendant). ?- ancestor(A,yossi). A = rachel ; A = rina ; false. Concepts: • predicate symbol, individual constant symbol, axioms (facts/rules), query. Semantics: • individual constant symbols - entities, axioms - relations of entities. • Quantification of variables (universal/existential) • Answers are partial substitutions to query variables (or true/false indications).
Operational Semantics for LP Input: a program P and a query Q Interpreter of LP: • Unify - pattern matching between an atomic formula from Q and a head of some rule/fact from P. • Answer-query (proof-tree)- Create a proof tree. Back track from a leaf if it is a "dead end" fail leaf, or if it is a success leaf and there may be additional answers to the query.
Unification The unification operation: two atomic formulas ==> substitution p(3, X), p(Y, 4) ==> {X = 4, Y = 3} p(X, 3, X), p(Y, Z, 4) ==> {X = 4, Z = 3, Y = 4} • substitution - a finite mapping, s, from variables to terms, such that s(X)≠X. Examples: s={X=4, Y=4, Z=3} {X = 4, Z = 3, U = X}, {X = 4, Z = 3, U = V } Not substitutions: {X = 4, Z = 3, Y = Y }, {X = 4, Z = 3, X = Y }
Application of Substitution atomic formula ◦ substitution ==> atomic formula' p(X, 3, X, W ) ◦ {X = 4, Y = 4} = p(4, 3, 4, W) p(X, 3, X, W ) ◦ {X = 4, W = 5} = p(4, 3, 4, 5) p(X, 3, X, W ) ◦ {X = W, W = X} = p(W, 3, W, X) • A unifier of atomic formulas A and B is a substitution s, such that A◦s = B◦s. • The unification operation returns a unifier. • Goal of Unify(A,B): find the most general unifier. Unify( p(X, 3, X, W), p(Y, Z, 4, W ) ) ==> {X=4, Y=4, Z=3} p(X, 3, X, W ) ◦ {X=4, Y=4, Z=3} = p(4, 3, 4, W ) p(Y, Z, 4, W ) ◦ {X=4, Y=4, Z=3} = p(4, 3, 4, W) • Less general unifiers {X = 4, Z = 3, Y = 4, W = 5}, {X = 4, Z = 3, Y = 4, W = 0}
Instantiation and Generalization • An atomic formula A’ is an instance of an atomic formula A if there is a substitution s such that A◦s = A’ • A is more general than A’ if A’ is an instance of A
Most General Unifier (MGU) • mgu of atomic formulas A and B is a unifier s of A and B such that A◦s = B◦s is more general than all other instances of A and B obtained by applying a unifier
Combination of substitutions s ◦ s' • s' is applied to the terms of s • A variable X for which s(X) is defined, is removed from the domain of s' • The modified s' is added to s. • Identity bindings are removed. {X = Y, Z = 3, U = V } ◦ {Y = 4, W = 5, V = U, Z = X} ={X = 4, Z = 3, Y = 4, W = 5, V = U}.
Disagreement Set • The disagreement set of atomic formulas is the set of left most symbols on which the formulas disagree. disagreement-set(p(X, 3, X, W ), p(Y, Z, 4, W )) = {X, Y }. disagreement-set(p(5, 3, X, W ), p(5, 3, 4, W )) = {X, 4}.
Unify - A unification algorithm Signature: unify(A, B) Type: atomic-formula*atomic-formula -> a substitution or FAIL Post-condition: result = mgu(A, B) if A and B are unifiable or FAIL, otherwise
Unify - examples 1. unify[ p(X, 3, X, W), p(Y, Y, Z, Z) ] ==> help[ {} ] ==> D = {X, Y} help[ {X = Y } ] ==> D = {Y, 3} help[ {X = 3, Y = 3 } ] ==> D = {Z, 3} ] help[ {X = 3, Y = 3, Z = 3 } ] ==> D = {W, 3} help[ {X = 3, Y = 3, Z = 3, W = 3 } ] ==> {X = 3, Y = 3, Z = 3, W = 3 } 2. unify[ p(X, 3, X, 5), p(Y, Y, Z, Z) ] ==> FAIL
Properties of unify(A, B) algorithm: • The algorithm always terminates. • Unification is a generalization of Pattern matching • If B does not include variables and A does not include repeated variable occurrences, the time complexity can be linear.
Operational Semantics for LP Interpreter of LP: • Unify - pattern matching between an atomic formula from Q and a head of some rule/fact from P. • Answer-query (proof-tree)- Create a proof tree. Back track from a leaf if it is a "dead end" fail leaf, or if it is a success leaf and there may be additional answers to the query.
answer-query: an interpretation algorithm for LP Input: A query: Q = ?- Q1, ..., Qn. Each component is called goal A program P , with numbered rules (denoted by number(R)) A goal selection policy Gsel A rule selection policy Rsel Output: A set of (possibly partial) substitutions for variables of Q. General Idea: Repeated effort to select a goal using roles.
answer-query Algorithm • PT := proof-tree(make_node(Q)) • Return {s | s ∈ labels(Success(P T ))/Q }, where Success(PT) is the set of Success nodes of P T , and labels/Q is the restriction of the substitutions in labels to the variables of Q.
proof-tree(current_node) If label(current_node) is ?- true, ..., true. 1. Mark current_node as a Success node 2. If the path from the tree root to current_node is labeled with the substitutions s1, . . . , sn, label current_node with the substitution s1 ◦ s2 ◦ . . . ◦ sn Else 1. Select a goal G true in label(current_node) according to Gsel. 2. Rename variables in every rule and fact of P . 3. While has-next?(iterator(current_node)): (a) Advance iterator: next(iterator(current_node)) (b) Rule selection: Starting from iterator(current_node), and according to Rsel, select a rule R = [A :- B1, ..., Bm.] such that Unify(A, G) = s' succeeds with the unifying substitution s'. (c) Rule application: if a rule R is selected then i. Construct a new query node by removing G, adding the body of R, and applying s' to the resulting query: new_node = make_node([label(current_node)−G+B1,...,Bm]◦s') ii. Add a child node and start a new proof: add_child(current_node, < s', number(R) >, (new_node)) proof-tree(new_node)
Comments about answer-query • Variable renaming according to depth in tree. Xi at depth i. • Unify(A,G), where G is the selected goal and A the head of the selected rule. • Let XG is a variable from G and XA a variable of A • Selecting XA=XG or XG=XA does not change query results. • Selecting XA=XG leaves the query variables in the tree. • The goal and rule selection decisions can affect the performance of the interpreter.
Example 6.5 % Signature: father(F,C)/2 parent(abraham,isaac). %1 parent(isaac, jacob). %2 parent(haran,lot). %3 parent(haran,yiscah). %4 parent(haran,milcah). %5 % Signature: male(P)/1 male(isaac). %1 male(lot). %2 % Signature: son(C, P)/2 son(X, Y) - parent(Y, X), male(X). %1 % Signature: ancestor(Ancestor, Descendant)/2 anc(Anc, Des) :- parent(Anc, Des). %1 anc(Anc, Des) :- parent(Anc, Person), %2 anc(Person, Des).
?- anc(abraham, D). What happens if rules 1 and 2 of 'anc' are switched?
What happens if bodies 1 and 2 in rule 2 of 'anc' are switched?