I've an algorithm as follows -
(defn max-of
[args]
(into [] (apply map #(apply max %&) args)))
which works fine.
(max-of [[1 7] [3 5] [7 9] [2 2]])
returns [7 9]
It basically finds the maximum element on each position. 7 is the largest first element is the collection and 9 is the largest second element. However, when trying to use reducer/map
from core.reducers
, i get
CompilerException clojure.lang.ArityException: Wrong number of args (21) passed to: reducers/map
So this does not work -
(defn max-of
[args]
(into [] (apply r/map #(apply max %&) args)))
Why?
UPDATE
my final code is
(defn max-of [[tuple & tuples]]
(into [] (r/fold (fn
([] tuple)
([t1 t2] (map max t1 t2)))
(vec tuples))))
Running a quick bench on it gives Execution time mean : 626.125215 ms
I've got this other algorithm that I wrote before -
(defn max-fold
[seq-arg]
(loop [acc (transient []) t seq-arg]
(if (empty? (first t))
(rseq (persistent! acc))
(recur (conj! acc (apply max (map peek t))) (map pop t)))))
which does that same thing. For this i got - Execution time mean : 308.200310 ms
which is twice as fast than the r/fold parallel thingy. Any ideas why?
Btw, if I remove into []
from the r/fold
stuff, then I get Execution time mean : 13.101313 ms
.
r/map
takes [f]
or [f coll]
- so your apply
approach won't work here
user=> (doc r/map)
-------------------------
clojure.core.reducers/map
([f] [f coll])
vs.
user=> (doc map)
-------------------------
clojure.core/map
([f] [f coll] [f c1 c2] [f c1 c2 c3] [f c1 c2 c3 & colls])
The answer to the question why has already been given. So let's answer the next question: "what are you trying to do?"
According to how i've understood your goal (find maximum elements by the position in tuples) and to do it potentially in parallel (as you are trying to use reducers), that's what you have to do
(defn max-of [tuples]
(r/fold (fn
([] (first tuples))
([t1 t2] (map max t1 t2)))
((rest tuples)))
user> (max-of [[1 7] [3 5] [7 9] [2 2]])
(7 9)
(max-of [[1 2 3] [3 2 1] [4 0 4]])
(4 2 4)
user> (max-of [])
nil
user> (max-of [[1 2 3]])
[1 2 3]
or even better with destructuring:
(defn max-of [[tuple & tuples]]
(r/fold (fn
([] tuple)
([t1 t2] (map max t1 t2)))
tuples))
update: for large data you should optimize it and switch to using vectors
(defn max-of [[tuple & tuples]]
(r/fold (fn
([] tuple)
([t1 t2] (map max t1 t2)))
(vec tuples)))
user> (max-of (repeat 1000000 [1 2 3 4 5 6 7 8 9 10]))
(1 2 3 4 5 6 7 8 9 10)
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.