【发布时间】:2014-01-19 05:18:42
【问题描述】:
我有这个问题,我需要给出一个解决方案来避免两个子句中的递归调用f(T,S):
f([],0).
f([H|T],S):-
f(T,S1),
S1>=2,
!,
S=S1+H.
f([_|T],S):-
f(T,S1),
S=S1+1.
我不明白这是做什么的... 而且我真的不知道如何避免这种递归调用。 请帮我解决一下
【问题讨论】:
-
任务不是避免non-tail递归调用吗?上面的代码是计算列表中元素的总和,没有递归就没有简单的方法(我不知道)。
-
该谓词不计算总和。实际上,对于像
[1,2,3,4]这样的列表,它会导致S = 0+1+1+2+1。所以它需要一些工作。一个问题是,在 prolog 中,=/2不是 算术赋值语句。要分配算术表达式,请使用is/2。 -
你说得对,我忘了
is/2。不过,我认为没有递归是不可能做到的。 -
@Świstak35 实际上,我认为在这种情况下,OP 使用
=是可以的。我没有注意到 Turbo Prolog 标签。 Turbo Prolog 允许将=用作is(不知道为什么,但确实如此)。我同意:递归是唯一简单的方法,但是正如您所指出的,可以在尾递归和非尾递归之间进行选择。 -
@Świstak35 在对谓词感到困惑之后,我意识到它不会计算列表的总和(如它第一次出现的那样),而是将列表头部的值添加到其主体的长度.奇怪,那个。
标签: prolog