有了新的 clojure 1.7,我决定了解在哪里可以使用传感器。我了解它们可以带来什么好处,但是我找不到编写带有解释的自定义换能器的正常示例。
好的,我试图测试发生了什么。我打开了 clojure 文档。还有一些例子xf
用作论据。第一:这个 xf 或 xfrom 是什么意思?这个东西产生了身份传感器。
(defn my-identity [xf]
(fn
([]
(println "Arity 0.")
(xf))
([result]
(println "Arity 1: " result " = " (xf result))
(xf result))
([result input]
(println "Arity 2: " result input " = " (xf result input))
(xf result input))))
[result input]
我从文档示例中获取了变量的命名。我认为这就像在减少功能中result
减少部分并且input
是新的集合元素。
所以当我做的时候,(transduce my-identity + (range 5))
我得到10
了我所期待的结果。然后我读到了eduction
,但我不明白它是什么。无论如何,我做了(eduction my-identity (range 5))
并得到:
Arity 2: nil 0 = nil
Arity 2: nil 1 = nil
Arity 1: nil = nil
(0 0 1 1)
xf
因为我在println
声明中调用,所以每个项目都重复了。为什么它将每个项目重复两次?为什么我是零?进行推理时我总是会得到 nil 吗?我可以转发这种行为吗?
反正我做到了
> (reduce + (eduction my-identity (range 5))
clojure.core.Eduction cannot be cast to clojure.lang.IReduce
好的,结果是Eduction
不可约的,但像列表一样打印。为什么不能还原?当我打字时(doc eduction)
,我明白了
Returns a reducible/iterable application of the transducers
to the items in coll.
不应该(transduce xform f coll)
和(reduce f (eduction xfrom coll))
一样吗?
我做了
> (reduce + (sequence my-identity (range 5))
20
当然我是20
因为重复。我再次认为应该是这样,(transduce xform f coll)
并且(reduce f (sequence xfrom coll))
至少在没有任何有状态转换器的小例子中总是相等的。这是愚蠢的,他们不是,还是我错了?
好的,然后我尝试(type (sequence my-identity (range 5)))
获取 clojure.lang.LazySeq 我认为它很懒,但是当我尝试获取first
元素时,clojure 一次计算了所有序列。
所以我的总结:
1) xf 或 xform 是什么意思?
2)为什么我得到nil
作为result
论点 while eduction
or sequence
?
3)我可以始终确定它会是nil
whileeduction
还是sequence
?
4) 什么是eduction
不可还原的惯用想法,什么是惯用的想法?或者如果是,那么我该如何减少它?
sequence
5) 为什么我在or时会出现副作用eduction
?
6) 我可以用传感器创建实际的惰性序列吗?