2
votes

I created knowledge base a.pl as follows:

sunny. rainy. god_YES.

Now in Prolog, after I run consult('a.pl'). it gets compiled and also gives true for stored facts. That is ..

?- sunny.
true.

But for some other fact, it doesn’t return false. For example..

?- not_sunny.

Which returns..

ERROR: toplevel: Undefined procedure: not_sunny/0 (DWIM could not correct goal)

2

2 Answers

2
votes

Your Prolog fact database needs true/false assertions about the predicates you'd like to query about. A fact database like:

 sunny.
 rainy.

is actually interpreted as the following predicates:

 sunny :- true.
 rainy :- true.

These predicates (sunny/0 and rainy/0) could have had false instead of true as the clause body.

A query like:

?- not_sunny. 

will only work if there is a predicate not_sunny/0 in the database already. Otherwise, such a query will generate the error you've shown, as not_sunny/0 is an 'undefined procedure'. Instead, you could have asked:

?- \+ sunny.

This uses the negation operator (\+) in front of a known predicate, sunny/0. With the database above, given ?- sunny. is true, this query will evaluate to false as you might otherwise have been expecting from ?- not_sunny.

For more information on Prolog basics, I can highly recommend the site Learn Prolog Now (http://www.learnprolognow.org/).

0
votes

sharky already answered that Prolog expects a known predicate in a query and how to encode the query in a better way. But principally it is not unreasonable to expect that a query like not_sunny would just fail because of Prolog's "closed world assumption": If it is not specified, it is not true.

There is a good reason for not just failing if the predicate does not exists: It is just by far more common that you have a typo in your program and it would be very painful to debug it if the query just fails.

But if you really want, you can actually alter the behaviour with the set_prolog_flag/2 predicate:

?- not_sunny.
ERROR: toplevel: Undefined procedure: not_sunny/0 (DWIM could not correct goal)
?- set_prolog_flag(unknown,fail).
Warning: Using a non-error value for unknown in the global module
Warning: causes most of the development environment to stop working.
Warning: Please use :- dynamic or limit usage of unknown to a module.
Warning: See http://www.swi-prolog.org/howto/database.html
true.

?- not_sunny.
false.