SWI-Prolog Prolog如何处理逻辑比较

时间:2011-12-30 21:18:52

标签: prolog comparison logical-operators

我在 SWI-Prolog:

中编写了以下代码
:- dynamic state_a/1 .
 :- dynamic state_b/1 .
 :- dynamic state_c/1 .
 state_a([1,2,3,4,5,0]).
 state_b([0]).
 chop(LIST,HEAD,TAIL) :- LIST=[HEAD|TAIL].
 move_ab :- !,state_a(X),
            chop(X,Ha,Ba),
            Ha>0,
            state_b(Y),
            chop(Y,Hb,Bb),!,
            (Ha<Hb ; Hb =:= 0),
            asserta(state_a(Ba)),asserta(state_b([Ha|Y])),
            retract(state_a(X)), retract(state_b(Y));
            write('Wrong Move.Choose Another').

我的代码中有2个 OR(;)。当我第一次在Prolog中询问move_ab时,在第二个OR之前的所有条件都是真的,所以我从Prolog得到答案 true 。 但是我第二次在Prolog中问move_ab我只得到答案 false 。 我不知道这是怎么发生的。第二个OR之前的某些条件不正确,因此Prolog应该在第二个OR之后检查条件并写下消息错误移动。选择另一个。。 我尝试使用()对条件进行分组,但我仍然得到相同的消息。 关于发生了什么的任何想法?顺便说一下,我是Prolog的新手,刚刚开始2天前:)

1 个答案:

答案 0 :(得分:1)

问题在于使用cut(!/0之前条件是否经过适当测试。剪切删除选择点。这意味着在您测试任何内容之前删除选项。因此,如果测试失败,一切都会失败!

顺便说一下,操纵数据库可能不是最好的主意。要表示状态,可以使用全局变量,如下所示:

:- nb_setval(state_a, [1,2,3,4,5,0]).
:- nb_setval(state_b, [0]).

move_ab :-
    nb_getval(state_a, [Ha|Ta]),
    Ha > 0,
    nb_getval(state_b, [Hb|Tb]),
    (Ha < Hb ; Hb =:= 0),
    nb_setval(state_a, Ta),
    nb_setval(state_b, [Ha, Hb|Tb]),
    !
    ;
    write('Wrong Move.Choose Another').

对prolog中的初学者提出的一般建议是尽可能远离数据库操作,因为如果没有它,问题通常是可以解决的。虽然这可能是合理的,但全局变量将更快更容易操作。