【问题标题】:Clojure reduce transducerClojure 减少换能器
【发布时间】:2016-03-26 00:10:56
【问题描述】:

我正在寻找具有缩减功能的换能器的简单示例。 我希望以下内容会返回一个转换函数,因为(filter odd?) 就是这样工作的:

(def sum (reduce +))
clojure.lang.ArityException: Wrong number of args (1) passed to: core$reduce

我目前对换能器的理解是,通过省略集合参数,我们可以返回一个可以与其他换能函数组合的换能函数。为什么filterreduce 不一样?

【问题讨论】:

    标签: clojure reduce transducer


    【解决方案1】:

    reduce 函数 doesn't return a transducer。 之所以这样,是因为reduce 是返回可能是序列的值的函数。其他函数,如 filtermap 总是返回序列(甚至是空的),允许组合这些函数。

    要将某些内容与 reduce 函数结合,您可以使用 a reducer library 它提供了类似于您想要做的功能(如果我正确理解的话)。

    更新

    好吧,我的回答有点混乱。 首先让我们看看filtermap 和许多其他函数是如何工作的:这并不奇怪,所有这些函数都基于reduce,它是一个归约函数(这样,它们不'不要创建一个输入一个更大尺寸的集合)。因此,如果您以任何方式减少一些 coll - 您可以组合您的减少以在所有减少函数之间从可减少的 coll 传递可减少的值以获得最终值。这是提高性能的好方法,因为部分值有望以某种方式为零(作为转换的一部分),并且只有一个逻辑循环(我的意思是循环,您只迭代序列一次并将每个值传递给所有转变)。 那么,为什么reduce 函数如此不同,因为一切都建立在它之上?

    所有 traducer 都基于一个简单而有效的想法,在我看来,它看起来像筛子。但是减少可能只针对最后一步,因为结果只有一个值。因此,您可以在此处使用reduce 的唯一方法是提供coll 和简化形式。 筛子类比中的减少就像筛子下的漏斗: 你把你的集合,把它扔给一些函数,比如 map 和 filter 和 take - 正如你所看到的,作为转换结果的新集合的大小永远不会大于作为输入集合的大小。所以最后一步可能是reduce,它接受一个经过筛选的集合,并根据所做的一切取一个值。

    还有一个不同的函数,它允许您组合传感器和减速器 - transducer,但它也需要一个函数,因为它就像一个入口点,也是我们筛子的最后一步。

    reducers 库类似于传感器,也允许 reduce 作为最后一步。这只是制作与传感器相同的另一种方法。

    要实现你想做的,你可以使用partial 函数来代替。它会是这样的:

    (def sum
      (partial reduce +'))
    
    (sum [1 2 3])
    

    将返回6的明显答案

    【讨论】:

    • 我一定还是遗漏了一些东西。 (clojure.core.reducers/fold +) 抛出异常。
    • 我编辑了我的帖子以消除误解。希望能帮到你。
    猜你喜欢
    • 2018-10-29
    • 2020-03-25
    • 2014-09-26
    • 1970-01-01
    • 1970-01-01
    • 2011-03-10
    • 1970-01-01
    • 1970-01-01
    • 2014-09-06
    相关资源
    最近更新 更多