Recursion Lisp中的递归加法
我是一个初学者,我正在努力自学公共Lisp,在我的自学过程中,我编写了一个函数,我认为该函数适用于两个参数的递归加法。但是,该功能总是失败。为什么呢Recursion Lisp中的递归加法,recursion,lisp,common-lisp,addition,Recursion,Lisp,Common Lisp,Addition,我是一个初学者,我正在努力自学公共Lisp,在我的自学过程中,我编写了一个函数,我认为该函数适用于两个参数的递归加法。但是,该功能总是失败。为什么呢 (defun sum (n m) ;;;Returns the sum of n and m using recursion (cond ((eq m 0) n)) (sum (1+ n) (1- m))) 据我所知,它应该不断地向n添加1,同时递减m,直到m为0,在这一点上,递归加法是完整的进行这种加法确实是一个非常好的用例,但我将
(defun sum (n m)
;;;Returns the sum of n and m using recursion
(cond ((eq m 0) n))
(sum (1+ n) (1- m)))
据我所知,它应该不断地向n添加1,同时递减m,直到m为0,在这一点上,递归加法是完整的进行这种加法确实是一个非常好的用例,但我将向您解释您的错误在哪里:
(defun sum (n m)
;;;Returns the sum of n and m using recursion
(cond ((eq m 0) n)) ;; <= This line is ignored, you not returnin N.
(sum (1+ n) (1- m))) ;; <= this will be called forever
让我们跟踪它,看看它是如何工作的:
CL-USER> (sum 0 10)
0: (SUM 0 10)
1: (SUM 1 9)
2: (SUM 2 8)
3: (SUM 3 7)
4: (SUM 4 6)
5: (SUM 5 5)
6: (SUM 6 4)
7: (SUM 7 3)
8: (SUM 8 2)
9: (SUM 9 1)
10: (SUM 10 0)
10: SUM returned 10
9: SUM returned 10
8: SUM returned 10
7: SUM returned 10
6: SUM returned 10
5: SUM returned 10
4: SUM returned 10
3: SUM returned 10
2: SUM returned 10
1: SUM returned 10
0: SUM returned 10
10
如果您愿意接受建议,请不要尝试使用递归做这种奇怪的事情,如果您想学习如何使用它,请尝试将其用于一些自然的递归情况,如阶乘、斐波那契、树处理等。我想您有两个简单的输入错误:
cond
子句中缺少t
李>
你的意思可能是:
(defun sum (n m)
(cond
((eq m 0) n) ; here you had one parenthesis too many
(t (sum (1+ n) (1- m))))) ; here you were missing the `t` symbol
您可以递归调用
SUM
。当堆栈溢出时,它停止。也许你应该改善一下状况,让它停止自鸣。。。如果,请尝试使用。另外,EQ
不适用于数字。使用EQL
或=
。根据代码,缩进是正确的cond
做一些被丢弃的事情(n
或nil
),然后通过添加n
和减少m
无条件递归。它不会返回nil
,因为它不会停止。你收到堆栈溢出消息了吗?@Sylvester是的,我在Emacs中收到堆栈溢出消息。研究其他人对我的纠正向我展示了我是如何把cond语句搞砸的,以及为什么递归永远不会结束。或者至少让cond
测试表单彼此对齐。如果cond与对sum的递归调用不在同一级别,则很容易发现错误。当然,他可以使用cond,但是如果只有两个分支,if是惯用的。是的,显然if在这里更惯用。只要提到cond,以防OP在其他情况下遇到类似的问题,cond将是惯用的。谢谢。我认为我对Lisp的理解要好得多,并且可以看出我的代码失败的原因。我当然会接受你的建议,坚持更自然的递归问题:)OP的用例是一个标准的教科书示例,在大学的可计算性课程中使用递归来建立原始操作。谢谢。我原以为我的代码完全错了,但看到我还有两个小的打字错误,这有点令人鼓舞。@BurnedOut不,你差得太近了。虽然我在这里也会使用if
而不是cond
,但有些人出于各种原因建议始终使用cond
,例如。
(defun sum (n m)
(cond
((eq m 0) n) ; here you had one parenthesis too many
(t (sum (1+ n) (1- m))))) ; here you were missing the `t` symbol