Skip to content

Instantly share code, notes, and snippets.

@apbendi
Last active August 29, 2015 14:01
Show Gist options
  • Select an option

  • Save apbendi/4a8bc62dbe0db678ab07 to your computer and use it in GitHub Desktop.

Select an option

Save apbendi/4a8bc62dbe0db678ab07 to your computer and use it in GitHub Desktop.
A Clojure Noob's 4clojure solutions
; A work in progress: a clojure noob works through 4clojure.com problems.
; Solutions here are by NO MEANS the best way to do these problems.
; Learning as I go here!
; #1
true
; #2
4
; #3
"HELLO WORLD"
; #4
:a :b :c
; #5
(list 1 2 3 4)
; #6
:a :b :c
; #7
[1 2 3 4]
; #8
(set (list :a :b :c :d))
; #9
2
; #10
20
; #11
[:b 2]
; #12
3
; #13
(list 20 30 40)
; #14
8
; #15
(fn [x] (* 2 x))
; #16
#(str "Hello, " % "!")
; #17
(list 6 7 8)
; #18
(list 6 7)
; #19
(fn [a-seq]
(loop [s a-seq]
(if (= 1 (count s))
(first s)
(recur (rest s)))))
; #20
(comp first rest reverse)
; #21
(fn [a-seq n]
(loop [s a-seq n-count 0]
(if (= n n-count)
(first s)
(recur (rest s) (inc n-count)))))
; #22
(fn [a-seq]
(loop [s a-seq n 0]
(if (empty? s)
n
(recur (rest s) (inc n)))))
; #23
(fn [a-seq]
(loop [s a-seq rev ()]
(if (empty? s)
rev
(recur (rest s) (conj rev (first s))))))
; #24
reduce +
; #25
filter #(odd? %1)
; #26
(fn [n-max]
(loop [n 2 s (list 1 1)]
(if (= n n-max)
(reverse s)
(recur (inc n) (conj s (+ (first s) (second s)))))))
; #27
(fn[x]
(if (string? x)
(= (apply str (reverse x)) x)
(= (reverse x) x)))
; #28
(fn flt [coll]
(loop [s coll
fl ()]
(if (empty? s)
fl
(let [l (first s)
rs (rest s)]
(if (sequential? l)
(recur rs (concat fl (flt l)))
(recur rs (concat fl (list l))))))))
; #29
#(apply str (re-seq #"[A-Z]+" %))
; #30
(fn [a-seq]
(loop [s a-seq
deduped []
last nil]
(if (empty? s)
deduped
(if (= (first s) last)
(recur (rest s) deduped (first s))
(recur (rest s) (conj deduped (first s)) (first s)))))
; #31
#(partition-by identity %)
; #32
(fn [coll]
(apply concat (map #(repeat 2 %) coll)))
; #33
(fn [coll n]
(apply concat (map #(repeat n %) coll)))
; #34
(fn [start end]
(loop [curr start
coll (list start)]
(if (= curr (- end 1))
(reverse coll)
(recur (inc curr) (conj coll (inc curr))))))
; #35
7
; #36
[z 1 y 3 x 7]
; 37
"ABC"
; #38
(fn [& args]
(reduce #(if (>%1 %2) %1 %2) args))
; #39
#(apply concat (map vector %1 %2))
; #40
(fn [x coll]
(let [xcoll (repeat (count coll) x)
lcoll (mapcat vector coll xcoll)
n (- (count lcoll) 1)]
(take n lcoll)))
; #41
(fn [coll n]
(loop [s coll no-nths ()]
(if (< (count s) n)
(concat no-nths s)
(recur (nthrest s n) (concat no-nths (take (- n 1) s))))))
; #42
(fn [x]
(reduce * (map inc (range x))))
; #43
#(apply map list(partition %2 %1))
; #44
(fn [x coll]
(let [n (mod x (count coll))]
(concat (nthrest coll n) (take n coll))))
; #45
(take 5 (iterate #(+ 3 %) 1))
; #46
(fn [f]
(fn [a b] (f b a)))
; #47
4
; #48
6
; #49
#(list (take %1 %2) (nthrest %2 %1))
; #50
(fn [coll]
(filter (complement empty?)
(list (filter sequential? coll)
(filter number? coll)
(filter keyword? coll)
(filter string? coll))))
; #51
[1 2 3 4 5]
; #52
[c e]
; #54
(fn [n a-seq]
(loop [s a-seq
r ()]
(if (< (count s) n)
(reverse r)
(recur (nthrest s n) (conj r (take n s))))))
; #55
(fn [coll]
(let [uniqs (set coll)]
(into {}
(for [x uniqs
:let [n (count (filter #(= x %) coll))]]
{x n}))))
; #56
(fn [coll]
(let [in? #(contains? (set %1) %2)]
(loop [uniq ()
c coll]
(if (empty? c)
(reverse uniq)
(if (in? uniq (first c))
(recur uniq (rest c))
(recur (conj uniq (first c)) (rest c)))))))
; #57
'(5 4 3 2 1)
; #58
(fn [f g & more]
(if (empty? more)
(fn [& args] (f (apply g args)))
(recur (fn [& args] (f (apply g args))) (first more) (rest more))))
; #59
(fn [& fns]
(fn [& args]
(for [f fns]
(apply f args))))
; #61
#(reduce into (map hash-map %1 %2))
; #62
(fn my-it [f x]
(cons x (lazy-seq (f x) (my-it f (f x)))))
; #63 seems awfully complex
(fn [f s]
(let [f-results (map (partial (fn [g x]
(list (g x) x)) f) s)
f-keys (distinct (map first f-results))
f-hash (reduce into (map hash-map f-keys (repeat [])))]
(loop [r-pairs f-results
r-hash f-hash]
(if (= 0 (count r-pairs))
r-hash
(let [r-key (first (first r-pairs))
r-val (second (first r-pairs))]
(recur (rest r-pairs) (assoc r-hash r-key
(conj (get r-hash r-key) r-val))))))))
; #66
(fn gcd [x y]
(loop [a x
b y]
(if (= 0 b)
a
(recur b (mod a b)))))
; # 68
; Complicated, just for fun!
(map (partial + 2) [5 4 3 2 1])
; #71
last
; #72
#(reduce + %)
; #81
(fn [s1 s2]
(reduce into #{} (map #(if ((partial contains? s1) %) #{%}) s2)))
; #83
(fn [& args]
(if (every? identity args)
false
(true? (some identity args))))
; #88
(fn [s1 s2]
(set (into (filter #(not (contains? s2 %)) s1) (filter #(not (contains? s1 %)) s2))))
; #90
(fn [s1 s2]
(reduce into #{} (map #(map vec (map (partial list %) s2)) s1)))
; #95
(fn is-tree? [s]
(if (false? s) ; not totally sure why I need this!
false
(if (not (coll? s))
true
(if (not= 3 (count s))
false
(and (is-tree? (second s)) (is-tree? (nth s 2)))))))
; #99 - Pro tip, as suspected, there is a smart way to do this using string trickery
(fn [x y]
(let [product (* x y)
after10 (fn [x] (Math/round (Math/floor ((partial * 0.1) x))))]
(loop [p product
digits ()]
(if (> p 0)
(recur (after10 p) (conj digits (mod p 10)))
digits))))
; #100
(fn [a b & more]
(let [gcd (fn [x y]
(loop [a x
b y]
(if (zero? b)
a
(recur b (mod a b)))))
lcd #(/ (* %1 %2) (gcd %1 %2))]
(if (empty? more)
(lcd a b)
(recur (lcd a b) (first more) (rest more)))))
; #107
; Pro tip, MUCH easier wat to do this with repeat & reduce
; STOP thinking about everything in loops and START thinking
; in terms of operations over data abstractions.
(fn [n]
(fn [x]
(loop [times 0
result 1]
(if (< times n)
(recur (inc times) (* x result))
result))))
; #118
(fn my-map [f s]
(lazy-seq
(when-let [coll (seq s)]
(cons (f (first coll)) (my-map f (rest coll))))))
; #120
(fn [s]
(reduce + (map (fn [x]
(let [y (reduce + (map #(reduce * (repeat 2 %)) (map (comp read-string str) (str x))))]
(if (< x y) 1 0))) s)))
; #122
(fn [b]
(loop [bs b
snum 0]
(if (> (count bs) 0)
(if (= (first bs) \1)
(recur (rest bs) (+ snum (apply * (repeat (count (rest bs)) 2))))
(recur (rest bs) snum))
snum)))
; 126
java.lang.Class
; #128
(fn [card-st]
(let [suit-st (first card-st)
rank-st (second card-st)]
{:suit (case suit-st
\D :diamond
\H :heart
\C :club
\S :spade),
:rank (case rank-st
\2 0
\3 1
\4 2
\5 3
\6 4
\7 5
\8 6
\9 7
\T 8
\J 9
\Q 10
\K 11
\A 12) } ))
; #134
; Pro tip: way easier with contains? and nil?
(fn [a-key a-map]
(if (a-key (set (keys a-map)))
(if (a-key a-map)
false
true)
false))
; #135
(fn [& infs]
(loop [result (first infs)
nums (rest (filter integer? infs))
ops (filter (complement integer?) infs)]
(if (empty? nums)
result
(recur ((first ops) result (first nums)) (rest nums) (rest ops)))))
; #143
#(apply + (map * %1 %2))
; #145
(map inc (list 0 4 8 12 16 20 24 28 32 36))
; #146
; Despite being almost explicitly told to by the instructions, I solved this without using
; the for macro because it wasn't clicking in my head how to. Unsurprisingly, my answer
; is way more complicated than it needs to be. The key to doing this "correctly" is to
; 1. Realize that for bindings do destructuring and 2. Understand how destructuring works with a map
(fn [a-map]
(reduce into {} (map (fn [m]
(let [k (key m)
v (val m)
path-to (partial #(hash-map (vec (list %1 %2)) %3) k)]
(map (fn [mm]
(let [kk (key mm)
vv (val mm)]
(path-to kk vv))) v))) a-map)))
; #153
(fn [ss]
(let [ss-count (apply + (map count ss))
combo-count (count (reduce into ss))]
(= ss-count combo-count)))
; #156
(fn [x coll]
(apply merge (map #(hash-map % x) coll)))
; #157
(fn [coll]
(let [calc-index (partial - (dec (count coll)))]
(loop [s coll
res ()]
(if (empty? s)
(reverse res)
(let [new-s (rest s)
value (first s)
index (calc-index (count new-s))]
(recur new-s (conj res (list value index))))))))
; #161
#{1 2 42}
; #162
1
; #166
(fn [f-less x y]
(if (f-less x y)
:lt
(if (f-less y x)
:gt
:eq)))
; #173
f s
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment