Tun
Tun

Reputation: 53

Difference between two Implementation of even and odd in Prolog

i have two implementation of Prolog , the Function is to decide if the given number is odd or even

the first one works correctly

even1(0).
even1(X) :- X>0 ,X1 is X-1, odd1(X1).

odd1(1).
odd1(X) :- X>1 , X1 is X-1, even1(X1).

even1(2) returns true

but the second one doesnt work correctly

even2(0).
even2(X) :- X>0 , odd2(X-1).

odd2(1).
odd2(X) :- X>1 , even2(X-1).

even2(2) returns false can anyone explain to me whats is the difference between the two of them ?

Upvotes: 1

Views: 522

Answers (1)

Paulo Moura
Paulo Moura

Reputation: 18663

Prolog is a relational language, not a functional language. Thus, when you call odd2(X-1), the predicate argument, X-1, is not evaluated as an expression but interpreted as a compound term:

?- functor(X-1, Name, Arity).
Name =  (-),
Arity = 2.

You can check what happens when Prolog proves a query by using your system trace functionality:

?- trace.
true.

[trace]  ?- even2(2).
   Call: (8) even2(2) ? creep
   Call: (9) 2>0 ? creep
   Exit: (9) 2>0 ? creep
   Call: (9) odd2(2-1) ? creep
   Call: (10) 2-1>0 ? creep
   Exit: (10) 2-1>0 ? creep
   Call: (10) even2(2-1-1) ? creep
   Call: (11) 2-1-1>0 ? creep
   Fail: (11) 2-1-1>0 ? creep
   Fail: (10) even2(2-1-1) ? creep
   Fail: (9) odd2(2-1) ? creep
   Fail: (8) even2(2) ? creep
false.

Note that the expression 2-1-1 evaluates to zero but, being a compound term, the call even2(2-1-1) doesn't unify with your base case for the predicate, even2(0):

?- even2(2-1-1) = even2(0).
false.

?- 2-1-1 = 0.
false.

Therefore, Prolog tries the second clause and the call eventually fails the X>0 check. Note that >/2, by being an arithmetic comparison predicate, it does evaluate its arguments prior to the actual comparison.

Upvotes: 5

Related Questions