sort-by
を使用するには、注文または優先順位の値を指定する必要があります。マップを比較するカスタムコンパレータを実装するか、並べ替えに使用するキーを計算するsort-by
のkeyfnを定義することができます。 keyfnの解は以下の通りです。 keyfnリターンだけを使用すると、コンパレータを実装するよりも、要件に匹敵する同等の値が簡単に得られます。 Comparators Guideをご覧ください。
私たちは、その数値表現に文字列の優先度を変換する機能の定義を開始:
(let [priorities {"Medicore" 0
"Enormous" 1
"Weeny" 2}]
(defn priority->num [p]
(if-let [num (priorities p)]
num
(throw (IllegalArgumentException. (str "Unknown priority: " p))))))
(priority->num "Enormous")
;; => 1
今、私たちは、各マップの最大の優先度を計算する必要があります。
(defn max-priority-num [m]
(->> m
(vals)
(map (comp priority->num :priority))
(apply max)))
(max-priority-num {:1 {:priority "Medicore" :somekey "SomeValue"}
:2 {:priority "Enormous" :somekey "SomeValue"}
:3 {:priority "Weeny" :somekey "SomeValue"}})
;; => 2
今、私たちは最終的にsort-by
を使用することができます:
(def m1 {:1 {:priority "Medicore" :somekey "SomeValue"}
:2 {:priority "Medicore" :somekey "SomeValue"}
:3 {:priority "Weeny" :somekey "SomeValue"}})
(def m2 {:1 {:priority "Medicore" :somekey "SomeValue"}
:2 {:priority "Enormous" :somekey "SomeValue"}
:3 {:priority "Weeny" :somekey "SomeValue"}})
(def m3 {:1 {:priority "Medicore" :somekey "SomeValue"}
:2 {:priority "Medicore" :somekey "SomeValue"}
:3 {:priority "Medicore" :somekey "SomeValue"}})
(sort-by max-priority-num [m1 m2 m3])
;; =>
({:1 {:priority "Medicore", :somekey "SomeValue"},
:2 {:priority "Medicore", :somekey "SomeValue"},
:3 {:priority "Medicore", :somekey "SomeValue"}}
{:1 {:priority "Medicore", :somekey "SomeValue"},
:2 {:priority "Medicore", :somekey "SomeValue"},
:3 {:priority "Weeny", :somekey "SomeValue"}}
{:1 {:priority "Medicore", :somekey "SomeValue"},
:2 {:priority "Enormous", :somekey "SomeValue"},
:3 {:priority "Weeny", :somekey "SomeValue"}})
これは 'sort-by'よりも' max-key'ではずっと簡単です。 – amalloy
右@amalloy、私はOPを見落とした、すべての要素がソートされていない最大要素を取得したい! (max-key max-priority-num m1 m2 m3) 'または'(max-key max-priority-num mapsを適用する)の代わりに '(max-key-max-priority-num [m1 m2 m3] ) 'より良いでしょう。 –