Hello! Are there any suggestions for improving this?
(defn opposite-pairs [start end]
(let [coll (range start (+ 2 end))
max (last coll)]
(->> coll
(take (-> (count coll) (/ 2)))
(mapcat
(fn [x]
(let [other (- max x)]
(if (= x other)
[x]
[x other]))))
(run! println))))
Reference output:
user> (opposite-pairs 1 999)
1
999
2
998
3
997
4
996
5
[...]another option:
(defn opposite-pairs [start end]
(let [numbers (range start (inc end))]
(interleave numbers (reverse numbers))))
(take 10 (opposite-pairs 1 999))
;; => (1 999 2 998 3 997 4 996 5 995)
I expect @serioga’s solution to be faster than mine, because I expect calculating every other number to be faster than reversing a list.No need for the reverse, range supports a step argument:
(interleave (range start (inc end))
(range end (dec start) -1))Isn't max just (+ 2 end) minus one?
I hate threading. 🙂 What is wrong with (/ (count coll) 2)?
Looking at the logic, I do not see a need to create the coll range (or the take). Just do a for loop up to half the difference between start and end, computing other as you do now -- that was insanely sloppy pseudo code -- I have to run -- but hopefully you get the idea.
@pavel.filipenco do you really need to work with sequences here?
(loop [start 1 end 999]
(when (< start end)
(println start end)
(recur (inc start) (dec end)))You can split your function up into a part that generates the numbers, and another that does something with them, in your case printing them.
(defn opposite-pairs [start end]
(cond
(< start end) (concat [start end] (opposite-pairs (inc start) (dec end)))
(== start end) [start]))
and then compose with println:
(run! println (opposite-pairs start end))General enough of a solution?
(defn converge [point & fns]
(loop [ms (map (fn [f] {:prev (f) :fn (f point)}) fns)
res []]
(if (empty? ms)
res
(recur
(->> ms
(map #(update % :prev (:fn %)))
(filter :prev))
(conj res (map :prev ms))))))
(defn from [start continue? step]
(fn
([] start)
([point]
(fn [prev]
(when (continue? prev point)
(step prev))))))
(comment
(->>
(converge 500
(from 999 #(> %1 (+ 1 %2)) #(- % 1))
(from 1 < #(+ % 1)))
(flatten)
(run! println)))