Prolog compiler return error

此生再无相见时 提交于 2019-12-12 20:46:40

问题


I have this hypothetical program to check if a path exists from point A to B.

/*city rules*/

edge(phx, tuc).
edge(tuc, ccg).
edge(ccg, sf).

connected(C1, C2) :-
   edge(C1, C2).
connected(C1, C2) :- 
   edge(C1, X),
   connected(X, C2).

the problem is it returns true, then false. Where is the false coming from?


回答1:


Let's look at the exact reply you got from Prolog! First you got a single true and on pressing SPACE or ; you eventually got:

?- connected(phx,sf).
true ;
false.

So you got true ; false. as the complete answer. The ; means "or". So Prolog essentially says: Your query connected(phx,sf). is the same as true ; false. So you need to look at the entire answer to understand what it means. Of course that is a bit odd, when true. would be good enough.

But first let's have another example:

?- connected(phx,X).
X = tuc ;
X = ccg ;
X = sf ;
false.

Here Prolog's complete answer is: connected(phx,X). describes the same set of solutions as X = tuc ; X = ccg ; X = fg ; false. which again would be shorter if false would be omitted.

So why does Prolog write out this false? Prolog computes the answers incrementally. It first shows you X = tuc and waits what you would do. In a sense, it is a bit lazy not to show you everything at once. Sometimes, Prolog does know that there will be no further answer, in that case, it writes a dot directly:

?- member(X,[1,2]).
X = 1 ;
X = 2.

Here Prolog says: dixi! I have spoken.

But sometimes, it is not that sure:

?- member(1,[1,2]).
true ;
false.

After proving that 1 is a member, it stops, otherwise it would have to explore the list further.

So this ; false. means: After the last answer/solution, Prolog was not yet sure that everything has been explored. This might be an inefficiency, it might be an indication that something can be improved. However, never, ever take this as pretext to insert a cut into your program. The cut in another answer is completely malaprop. It is the source for many, many errors. Before starting to use cuts you really should learn the other, pure part of Prolog, first.

BTW: Here is a better definition for connected/2 which avoids infinite loops by using closure/3 (click on it to get the definition).

connected(C0,C) :-
   edge(C0,C1)
   closure0(edge,C1,C).


来源:https://stackoverflow.com/questions/27255365/prolog-compiler-return-error

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!