你如何在Clojure中结合使用排序和过滤?

SCd*_*CdF 4 clojure

假设我有一个字符串集合,我希望返回超过4个字符的所有字符串,首先按最短字符串排序.

您可以通过以下方式解决这个问题:

(def strings ["this" "is" "super" "cool" "everybody" "isn't" "clojure" "great!?!?"])
(sort-by count < (filter #(> (count %) 4) strings))
;; > ("super" "isn't" "clojure" "everybody" "great!?!?")
Run Code Online (Sandbox Code Playgroud)

请注意我们使用了count两次.这可能在这里很好,但如果count不是count呢?如果不是count我们打电话super-expensive-function给我们,我们真的宁愿不跑得超过绝对必要,怎么办?

所以:

  • 我们有一系列的东西
  • 我们想要返回有序的东西集合
  • 使用计算上昂贵的函数的结果进行过滤和排序,每个事物只应调用一次

是否存在执行此操作的现有功能,还是需要构建自己的功能?

Mic*_*zyk 8

最简单的解决方案是将每个项目与其昂贵的计算属性配对,然后过滤和排序,然后丢弃参数:

(->> strings
     (map (juxt identity count))
     (filter (fn [[_ c]] (> c 4)))
     (sort-by peek)
     (map first))
Run Code Online (Sandbox Code Playgroud)

如果计算有问题的属性实际上是非常昂贵的,分配向量的开销应该几乎消失.