【问题标题】:Why this reduce function call does not work in Common Lisp?为什么这个 reduce 函数调用在 Common Lisp 中不起作用?
【发布时间】:2021-10-04 06:03:20
【问题描述】:

使用 Common Lisp (SBCL),我可以在 REPL 中成功评估:

CL-USER> (reduce #'+ '(1 2 3 4))
10

但是,这失败了:

> (reduce #'(lambda (e) (+ e 100))  '(1 2 3 4))

调试器抛出错误:

参数个数无效:2

我期待一个累积效应,所以总和应该是110

我怎样才能达到预期的效果?我需要使用reduce以外的其他东西吗?

【问题讨论】:

    标签: common-lisp reduce


    【解决方案1】:

    归约函数必须接受两个参数。您的 lambda 函数只接受一个。即使它有效,它也会在列表中添加的每个步骤中将100 添加到您的结果中。

    您的意思是指定初始值。最简单的 hacky 方法就是将其添加到您的列表中,例如

    > (reduce #'+ (cons 100 '(1 2 3 4)))
    110
    

    the specs 的正确方法是使用 :initial-value keyword parameter 明确指定它:

    > (reduce #'+ '(1 2 3 4) :initial-value 100)
    110
    

    如果您确实想在每个缩减步骤中添加100

    > (reduce #'(lambda (a x) (+ 100 a x)) '(1 2 3 4))
    310
    

    您可能还想通过将 is 指定为 :initial-value 来再添加一个 100

    【讨论】:

      【解决方案2】:

      调用(reduce #'f '(1 2 3 4)) 将计算

      (f (f (f 1 2) 3) 4)
      

      例如

      >>> (reduce #'(lambda (a b) (cons a b)) '(1 2 3 4))
      (((1 . 2) . 3) . 4)
      

      因此,您传递给reduce 的函数需要接受两个参数。首先使用序列的前两个元素调用此函数。然后使用前一次调用的结果和序列中的下一个元素调用该函数,依此类推(参见 [CLHS reduce])。要获得所有元素的总和,您需要调用以下代码:

      >>> (reduce #'(lambda (a b) (+ a b)) '(1 2 3 4))
      10
      

      reduce 的行为可以通过提供初始值来改变。调用

      (reduce #'f '(1 2 3 4) :initial-value 100)
      

      将计算以下内容:

      (f (f (f (f 100 1) 2) 3) 4)
      

      因此,如果你想得到想要的结果,你可以使用:

      >>> (reduce #'+ '(1 2 3 4) :initial-value 100)
      110
      

      要将每个数字加 100,然后计算总和,您可以使用 reducemapcar 的组合,这是函数式编程中的常见模式:

      >>> (reduce #'+ (mapcar #'(lambda (a) (+ a 100)) '(1 2 3 4)))
      410
      

      【讨论】:

      • 谢谢。那么如何在reduce的每个“迭代”中添加100呢?最终结果将是 410
      • @PedroDelfino 如果您想在每次迭代中添加 100,例如 (reduce '+ (mapcar (lambda (x) (+ x 100)) '(1 2 3 4)),您可以使用 :key 参数来减少:(reduce '+ '(1 2 3 4) :key (lambda (x) (+ x 100)))
      猜你喜欢
      • 2021-02-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-10-22
      • 2013-11-02
      • 1970-01-01
      相关资源
      最近更新 更多