使用递归的最大列表?

tra*_*jce 2 common-lisp

我的任务是在lisp中编写函数,通过使用递归来找到作为函数参数给出的列表的最大值.我尝试过但我有一些错误.我是Lisp的新手,我正在使用cusp插件进行eclipse.这是我的代码:

(defun maximum (l)
  (if (eq((length l) 1)) (car l)  
   (if (> (car l) (max(cdr l)))
    (car l) 
     (max (cdr l))
))
Run Code Online (Sandbox Code Playgroud)

dan*_*lei 16

如果这不是一个家庭作业问题,你应该喜欢这样的事情:

(defun maximum (list)
  (loop for element in list maximizing element))
Run Code Online (Sandbox Code Playgroud)

甚至:

(defun maximum (list)
  (reduce #'max list))
Run Code Online (Sandbox Code Playgroud)

(但是对于空列表,两者的行为都不同)

如果你真的需要一个递归解决方案,你应该尝试使你的函数更有效,和/或尾递归.看看迭戈和Vatine的答案,以获得更加惯用和高效的递归实现.

现在,关于你的代码:

在"Lisp方面"这是非常错误的,尽管你似乎对如何解决手头的问题有了一个想法.我怀疑你花了很多时间来学习lisp基础知识.括号混乱 - 缺少右括号,在中((length l) 1),您应注意评估列表中的第一个元素将用作运算符.此外,你没有真正递归,因为你试图打电话max(而不是maximize).最后,不要#'eq用于数字比较.此外,如果您以常规方式格式化和缩进代码,您的代码将更具可读性(不仅适用于其他代码).

你真的应该考虑花一些时间学习一个基本的Lisp教程,因为你的问题清楚地表明,即使是关于Lisp的最基本的东西,比如评估规则也缺乏理解.


Die*_*lla 5

我看到没有真正递归的答案,我写了一个只是为了练习Common-Lisp(目前正在学习).之前包含递归版本的答案效率很低,因为它会maximum递归调用两次.你可以写这样的东西:

(defun my-max (lst)
  (labels ((rec-max (lst actual-max)
             (if (null lst)
                 actual-max
                 (let ((new-max (if (> (car lst) actual-max) (car lst) actual-max)))
                   (rec-max (cdr lst) new-max)))))
    (when lst (rec-max (cdr lst) (car lst)))))
Run Code Online (Sandbox Code Playgroud)

这是(尾)递归和O(n).