在自定义clojure向量中计算重复项

end*_*gin 2 vector clojure

我正在尝试提出一个功能性解决方案来解释由交替集和数值组成的自定义数据结构中的重复项.

一个例子:

(def a [#{:a} 0.1 #{:b} 0.3 #{:a :b} 0.1 #{:a} 0.3 #{:b} 0.1 #{:a} 0.1])
Run Code Online (Sandbox Code Playgroud)

我想添加对应于重复集的值来导致

[#{:a} 0.5 #{:b} 0.4 #{:a :b} 0.1]
Run Code Online (Sandbox Code Playgroud)

我可以使用loop/recur但是想知道是否有一种在Clojure中使用高阶函数的方法.

谢谢.

Pio*_*dyl 5

(reduce
  (fn [acc [k v]]
    (update acc k (fnil + 0) v))
  {}
  (partition 2 a))
Run Code Online (Sandbox Code Playgroud)

首先,将序列划分为键值对,partition然后将reduce这些对划分为键值对.诀窍是使用fnil哪个将替换nil尚未添加到acc有价值的键0.

那给你一张地图:

{#{:a} 0.5, #{:b} 0.4, #{:b :a} 0.1}
Run Code Online (Sandbox Code Playgroud)

如果你需要它作为价值的平序列可以通过传递seqflatten:

(->> a
  (partition 2)
  (reduce
    (fn [acc [k v]]
      (update acc k (fnil + 0) v))
    {})
  (apply concat)
  (into []))

;; => (#{:a} 0.5 #{:b} 0.4 #{:b :a} 0.1)
Run Code Online (Sandbox Code Playgroud)