2024 年 Clojure 状态调查! 分享您的想法。

欢迎!有关如何使用本网站,请参阅 关于 页面获取更多信息。

0
Clojure

函数组合函数 comp 在像 (apply comp large-seq-of-fns) 这样的场景中效率非常低,因为它的大于 3 参数版本的会反转序列。

如果存在一个替代的 comp** (或任何其他) 函数就太好了,这个函数就像 comp 一样,但组合是从左到右的。

7 个答案

0

由:tsdh 发表评论

这是一个实现方法。

0

由:tsdh 发表评论

我的补丁有个奇怪的地方。使用 comp** 创建大量函数的大序列组合要比使用 comp 快得多,这是预期的,因为不需要反转序列。

然而奇怪的是,使用 comp 创建的组合评估大约比使用 comp** 快 10-20%,尽管 comp 的大于 3 参数版本是用 comp** 定义设定的:(apply comp* (reverse (list* f1 f2 f3 fs)))

有关基准测试的详细信息,请参阅: https://groups.google.com/d/msg/clojure/MizwTxHwLE4/hGLrMfetlP8J

0
_由:tsdh_ 发表评论

这里是些基准测试


user> (use 'criterium.core)
nil
user> (let [coll (doall (take 1000000 (repeat inc))
       f1(应用com* coll)
       f2(应用coll)
       (bench (f1 0) :verbose)
       (println "---------------------------------------")
       (bench (f2 0) :verbose)
amd64 Linux 3.4.2-gentoo 2核处理器
OpenJDK 64-Bit服务器虚拟机 22.0-b10
运行时参数:-agentlib:jdwp=transport=dt_socket,server=y,suspend=n -XX:+TieredCompilation -Xmx1G -Dclojure.compile.path=/home/horn/Repos/clj/testi/target/classes -Dtesti.version=0.1.0-SNAPSHOT -Dclojure.debug=false
评估次数             :600
             平均执行时间:112.324465 ms  95.0% CI:(112.247218 ms, 112.380682 ms)
    执行时间标准差:6.513809 ms  95.0% CI:(6.477450 ms, 6.553029 ms)
         执行时间下限:105.609401 ms  95.0% CI:(105.609401 ms, 105.622918 ms)
         执行时间上限:122.353763 ms  95.0% CI:(122.353763 ms, 122.405315 ms)
---------------------------------------
amd64 Linux 3.4.2-gentoo 2核处理器
OpenJDK 64-Bit服务器虚拟机 22.0-b10
运行时参数:-agentlib:jdwp=transport=dt_socket,server=y,suspend=n -XX:+TieredCompilation -Xmx1G -Dclojure.compile.path=/home/horn/Repos/clj/testi/target/classes -Dtesti.version=0.1.0-SNAPSHOT -Dclojure.debug=false
评估次数             :1440
             平均执行时间:43.519663 ms  95.0% CI:(43.516732 ms, 43.524062 ms)
    执行时间标准差:492.299089 us  95.0% CI:(490.829889 us, 494.198137 us)
         执行时间下限:42.781398 ms  95.0% CI:(42.781398 ms, 42.781398 ms)
         执行时间上限:44.157311 ms  95.0% CI:(44.157311 ms, 44.158513 ms)
nil

0
by

由:tsdh 发表评论

好的,我已经追踪到了性能差异。这来自于reverse创建了一个clojure.lang.PersistentList,它可以比一个(完全实现)的LazySeq迭代得更快。如果你在(apply comp* fncoll)中提供fncoll作为向量或列表,创建的合成应用与comp的速度一样快。

所以对我来说,这个补丁很好,也很有意义。

0
by

评论人:jafingerhut

补丁 0001-CLJ-1010-Add-a-left-to-right-version-of-comp-comp.patch,日期为2012年6月11日,在2014年9月5日或周围对Clojure进行一些提交后,不再干净地应用到最新的master分支。

我尚未检查此补丁是否易于更新。请参阅http://dev.clojure.org/display/community/Developing Patches中“更新过期补丁”部分,以获取有关如何更新补丁的建议。

0
by

由:tsdh 发表评论

以下是一个更新的补丁,适用于截至2014年9月8日的git master。

0
by
...