Evgenii.Balai
Evgenii.Balai

Reputation: 949

"NOT EXISTS" in swi-prolog

I'm stuck on a simple problem in prolog. Let's consider the program

worker(bill).
worker(smitt).
worker(fred).
worker(dany).
worker(john).
car(bmw).
car(mazda).
car(audi).
owner(fred,mazda).
owner(dany,bmw).
owner(john,audi).

I need to add one more predicate no_car(X),that will be true if the worker X has no cars,i.e,if we input a query ?:- no_car(X). the prolog should answer

X=smitt,
X=bill,
yes 

What i have done is

   hascar(X):-owner(X,_).
   nocar(X):- worker(X),not hascar(X).

But this approach does not work because anonimous variables are avaliable only for queries. So,i'm really stuck on this. I know there are "NOT EXISTS" words in SQL which allow to express this logic in a query,but is there something similar to them in prolog?

Upvotes: 1

Views: 4737

Answers (1)

ThomasH
ThomasH

Reputation: 23496

The following works for me and provides the expected result:

no_car(W):-
   worker(W),
   \+ owner(W, _).

Now this is close to what you have. For one thing, you can of course use _ in predicates; it is not restricted to queries. I usually use \* for negation, and not gives me a syntax error here!?

EDIT:

Ah! In my, albeit dated, version of Prolog you have to use not(hascar(X)) to make it work, so not/1 needs to be used as a term, not an operator. But the manual also says not is deprecated in favor of \+.

Upvotes: 7

Related Questions