【问题标题】:Lisp Reverse "all" FunctionLisp 反向“全部”函数
【发布时间】:2010-12-07 07:07:15
【问题描述】:

我想在 lisp 中编写一个函数,使用 map 函数反转列表中的所有元素,但我不知道如何开始这个。我想我必须以某种方式使用内置的 reverse 函数。 例如,如果我有列表 (1 2 3 (4 5 6 (7 8 9))) 我会得到 (((9 8 7) 6 5 4) 3 2 1) 或者如果我有列表 (1 2 3 (4 5) (6 7)) 我会得到 ((7 6) (5 4) 3 2 1) .. 任何帮助表示赞赏!

【问题讨论】:

  • 从下面的 cmets 来看,您似乎在描述一个递归问题,最简单的解决方案是递归函数(即调用自身的函数)。出于这个原因,我用“递归”标记了这个问题。

标签: recursion map lisp reverse


【解决方案1】:

只是一个快速的答案,不确定效率/优雅:

(defun reverse-deeply (list)
   (mapcar #'(lambda (li) 
               (cond
                ((consp li) (reverse-deeply li))
                (t li)))
           (reverse list)))

【讨论】:

  • 关键是递归。应该这样做。
  • 是的,就是这样。非常感谢!
【解决方案2】:
(defun reverse-list (list)
  (let ((result nil))
    (dolist (e list result)
      (push e result))))

【讨论】:

    【解决方案3】:

    这是一个适用于 Common-Lisp 的版本。

    (defun reverse-list (list)
        (if (atom list)
            list ;; Not actually a list, return the atom
          (reverse (mapcar #'reverse-list list)))
    
    ;; Testing it out
    (reverse-list '((1 2 3) (4 5 (3 6))))
    

    输出:

    (((6 3) 5 4) (3 2 1))
    

    Mapcar 是一个函数,它将另一个函数作为它的第一个参数,并将一个列表作为它的第二个参数。然后它在列表的每个元素上调用该函数。它返回所有答案的列表。因此,在我使用“mapcar”反转所有子列表之后,我再次调用“reverse”来反转更大的列表。

    它在每个子列表上调用的函数是'reverse-list'。这将检查列表是否是原子。如果是,那么它会返回自己。如果是列表,则对列表中的每个元素再次调用 mapcar,然后反转结果。

    【讨论】:

    • 这不是我想的那样..这个函数反转列表,但子列表的顺序也必须反转..
    • 如果有人不知道mapcar 是如何工作的,可能会造成混淆,因为有两种方法可以达到结果:a)反转顶级容器列表; b)反向成员列表:)
    • 这样更好吗?抱歉,我一定误解了你的要求。
    • @SnailBoy (reverse (mapcar #'reverse '((1 2 3) (4 5 6)))) 不明显吗?
    • 这也只反转了列表的 2 级.. 我需要它来反转列表的所有元素,包括子列表的子列表的子列表 .. 子列表的子列表的子列表等等 ..
    猜你喜欢
    • 2010-11-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-12-25
    • 2013-10-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多