为了账号安全,请及时绑定邮箱和手机立即绑定

Prolog后继符表示法产生不完整的结果和无限循环

/ 猿问

Prolog后继符表示法产生不完整的结果和无限循环

我开始学习Prolog,首先学习了后继符号。


这就是我在Prolog中编写Peano公理的地方。


参见PDF的第12页:


sum(0, M, M).

sum(s(N), M, s(K)) :-

    sum(N,M,K).


prod(0,M,0).

prod(s(N), M, P) :-

    prod(N,M,K),

    sum(K,M,P).

我将乘法规则放入Prolog。然后我执行查询:


?- prod(X,Y,s(s(s(s(s(s(0))))))).

这意味着基本上找到6的因数。


这是结果。


X = s(0),

Y = s(s(s(s(s(s(0)))))) ? ;

X = s(s(0)),

Y = s(s(s(0))) ? ;

X = s(s(s(0))),

Y = s(s(0)) ? ;

infinite loop

此结果有两个问题:


并未显示所有结果,请注意缺少结果X = 6,Y = 1。

除非我按Ctrl + C然后选择中止,否则它不会停止。

所以...我的问题是:


这是为什么?我尝试切换“ prod”和“ sum”。结果代码为我提供了所有结果。再说一遍,为什么呢?它仍然死循环。

如何解决?

我读了无限循环上的另一个答案。但是我希望有人根据这种情况做出回答。这对我有很大帮助。


查看完整描述

2 回答

?
慕瓜9086354

第一个问题(WHY)相当容易发现,特别是如果知道左递归。sum(A,B,C) 结合当C A和B 被结合,但原来的程序PROD(A,B,C)不使用绑定,以及不是与静止A,B未结合的递归。


如果我们交换sum,prod,我们将从sum中获得2个有用的绑定,以进行递归调用:


sum(M, K, P)

现在,M已绑定,将用于终止左递归。我们可以交换N和M,因为我们知道乘积是可交换的。


sum(0, M, M).

sum(s(N), M, s(K)) :-

    sum(N, M, K).


prod3(0, _, 0).

prod3(s(N), M, P) :-

    sum(M, K, P),

    prod3(M, N, K).

注意,如果我们交换M,K(即sum(K,M,P)),当prod3用P unknown调用时,我们仍然有一个非终止循环,但总之。


?- prod3(X,Y,s(s(s(s(s(s(0))))))).

X = s(s(s(s(s(s(0)))))),

Y = s(0) ;

X = s(s(s(0))),

Y = s(s(0)) ;

X = s(s(0)),

Y = s(s(s(0))) ;

X = s(0),

Y = s(s(s(s(s(s(0)))))) ;

false.

OT我对cTI报告感到困惑:prod3(A,B,C)terminates_if b(A),b(B); b(A),b(C)。


查看完整回答
反对 回复 2019-10-21
  • 2 回答
  • 0 关注
  • 175 浏览
我要回答

添加回答

回复

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信