代码之家  ›  专栏  ›  技术社区  ›  Daniel Yankowsky

Clojure:休息vs.下一个

  •  64
  • Daniel Yankowsky  · 技术社区  · 14 年前

    我很难理解 rest next 在Clojure。 The official site's page on laziness 指示首选项可能应使用 休息 但这并不能很清楚地解释两者之间的区别。有人能提供一些见解吗?

    4 回复  |  直到 9 年前
        1
  •  60
  •   sepp2k    14 年前

    如您所链接的页面所述, next 比(新行为)更严格 rest 因为它需要评估懒惰的缺点的结构来知道是否返回 nil 或者一个序列。

    休息 另一方面,始终返回seq,因此在实际使用 休息 . 换句话说, 休息 比…更懒惰 下一个 .

        2
  •  30
  •   limist    12 年前

    如果你有这个很容易:

    (next '(1))
    => nil
    

    所以 next 看下一件事,如果行为空,则返回 nil 而不是空序列。这意味着它需要向前看(它将返回的第一个项目),这使得它不完全懒惰(也许您不需要下一个值,但是 下一个 浪费计算时间。

    (rest '(1))
    => ()
    

    rest 不展望未来,只返回序列的其余部分。

    也许你会想,为什么还要在这里用两种不同的东西呢?原因是,您通常希望知道seq中是否没有剩余内容,然后返回 但在某些情况下,性能是非常重要的,并且评估一个项目可能意味着您可以付出巨大的努力。 休息 .

        3
  •  21
  •   rightfold Eugene Lazutkin    11 年前

    next 就像 (seq (rest ...)) .

    rest 将返回序列的其余部分。如果序列的那一部分还没有实现, 休息 不强制。它甚至不会告诉您序列中是否还有更多元素。

    下一个 执行相同的操作,但随后强制至少实现序列的一个元素。所以如果 下一个 退货 nil ,您知道序列中没有其他元素了。

        4
  •  2
  •   Terje Dahl    9 年前

    我现在更喜欢用 next 使用Reursion时,由于转义评估更简单/更清晰:

    (loop [lst a-list]
        (when lst
            (recur (next lst))
    

    VS

    (loop [lst a-list]
        (when-not (empty? lst)   ;; or (when (seq? lst)
            (recur (rest lst))
    

    使用的案例 rest 不过,如果您将集合用作队列或堆栈,则会出现这种情况。在这种情况下,您希望函数在弹出或取消最后一个项的排队时返回空集合。