Koleksiyondan rastgele öğeleri alan, aynı öğenin hiçbir zaman iki kez seçilmeyeceği bir işlev var. Bunun için bir çözüm varClojure'daki bir koleksiyondan n rasgele öğeler nasıl alınır?
(defn take-rand [n coll]
(take n (shuffle coll)))
Ama yani aynı tohum sağlandığında aynı rasgele alt kümesini döndürmek için gereken bir sinir bozucu gereksinimi,
(defn take-rand [n coll & [seed]])
(take-rand 5 (range 10) 42L) ;=> (2 5 8 6 7)
(take-rand 5 (range 10) 42L) ;=> (2 5 8 6 7)
(take-rand 5 (range 10) 27L) ;=> (7 6 9 1 3)
(take-rand 5 (range 10)) ;=> (9 7 8 5 0)
var: Ben oldukça kolay bunu başarabilir , ama biraz aksak ve çok deyimsiz hissediyor. Orada herhangi bir Clojure gazisi iyileştirmeler (veya tamamen farklı bir yaklaşım) önerebilir mi? İşte
ne yaptım:(defn take-rand
"Returns n randomly selected items from coll, or all items if there are fewer than n.
No item will be picked more than once."
[n coll & [seed]]
(let [n (min n (count coll))
rng (if seed (java.util.Random. seed) (java.util.Random.))]
(loop [out [], in coll, n n]
(if (or (empty? in) (= n 0))
out
(let [i (.nextInt rng n)]
(recur (conj out (nth in i))
(concat (take i in) (nthrest in (inc i)))
(dec n)))))))
memoize' içindir 'o şey bu değil tam olarak mı bu: Bu çözümü umut
beklediğiniz sonuçları olun: Size aşağıda benim çözüm gösterecektir sopanın yanlış ucu? Tekerleği yeniden icat etmediğiniz için – peter