Can prolog answer undetermined instead of just yes or no?

409 Views Asked by At

Suppose I have the knowledge base

likes(john,mary).
person(mary).
person(john).

If we ask prolog whether

|?- likes(mary,john)

It will answer no because we did not assert that. Is there any way to make prolog answer unknown unless we explicitly state.

\+ likes(mary,john)

In other words can we ask prolog to treat unbound expressions as possible rather than false. I've been using IDP system which permits existential quantification and treats non asserted relations as if unbound rather than false, but I would like to use something more mainstream. http://adams.cs.kuleuven.be/idp/server.html

For example in IDP you can make the statement

vocabulary V{
    type Person
    Likes(Person,Person)
}


theory T: V{

    //Everyone might like someone and disallow narcisiscm
    !x : ?y: Likes(x,y) & ~Likes(x,x).

}

//some instance without special meaning
structure S:V{
    Person={A..C}
}

procedure main(){
    //Print all possible solutions
    printmodels(allmodels(T,S))
}

Which yields

Number of models: 27
Model 1
=======
structure  : V {
  Person = { "A"; "B"; "C" }
  Likes = { "A","B"; "A","C"; "B","A"; "B","C"; "C","A"; "C","B" }
}
//...
2

There are 2 best solutions below

2
Thanos Tintinidis On BEST ANSWER

As stated, Prolog is using the closed-world assumption, i.e. asking if a fact is true means that we ask if we know it's true - a no means that we don't know if it's true, not that it's false. Of course, being a Turing-complete language you can simulate an open world - something like:

like(true, mary, john).
like(false, mary, nick).
like(unknown, X, Y).

Probably best to have some extra wrappers to deal with edge cases (e.g. having both true and false for a pair), and possibly use some higher-order predicate trick to avoid writing lots of boilerplate - but the core of the implementation is that you explicitly declare what's false, what's true and the rest is unknown.

0
mat On

What has been said so far is quite right: Prolog operates under the so-called Closed World Assumption (CWA). Still, I would like to offer a complementary perspective in addition to what has been posted already.

First, a Prolog program may not even terminate, and so we may never receive either of the possible answers you mention.

But even if the program does terminate, we may still obtain answers that are neither equivalent to true nor to false.

For example, using GNU Prolog:

| ?- X #\= 3.

X = _#2(0..2:4..127@)

Here, the answer is a pending constraint, a goal that is said to flounder because its truth is not definitely decided.

Such answers may or may not describe solutions.

For example:

| ?- fd_all_different([X,Y,Z]), fd_domain([X,Y,Z], 0, 1).

X = _#2(0..1)
Y = _#20(0..1)
Z = _#50(0..1)

yes

In this case, no solutions exist! To see this, we need to explicitly search for them:

| ?- fd_all_different([X,Y,Z]), fd_domain([X,Y,Z], 0, 1),
     fd_labeling([X,Y,Z]).

no

Thus, in the example above, it may really be more advisable to answer with maybe instead of yes.

Moreover, we know from fundamental logical theorems that such issues are unavoidable when reasoning over integers.

In this sense, Prolog systems can really give answers whose truth not only isn't, but moreover cannot be determined.