Friday, May 16, 2014

Clojure Koans Answers and Explanations - 5 - Maps

Here is the solution of Clojure Koans - maps - set 5.

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;1
(= __ (hash-map))
; Pretty much like sets there are 2 ways of creating
; maps. {} is the map counterpart of #{} in sets
(= {} (hash-map))


;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;2
(= __ (count (hash-map)))
; count is size() in Java
; for an empty map, it would be 0
(= 0 (count (hash-map)))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;3
(= {:a 1} (hash-map :a __))
; :a is mapped to 1
; Clojure compares values so
(= {:a 1} (hash-map :a 1))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;4
(= __ (count {:a 1 :b 2}))
; count is size() in Java
(= 2 (count {:a 1 :b 2}))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;5
(= __ (get {:a 1 :b 2} :b))
; get is equivalent to what it is in Java
; gets the mapped value for supplied key
(= 2 (get {:a 1 :b 2} :b))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;6
(= __ ({:a 1 :b 2} :a))
; this is the alternative way of looking up
; (looking up as in a hashtable, not in life) :-)
; the usage in this example is using a map
; as a lookup function
; taking an argument as searchable value
(= 1 ({:a 1 :b 2} :a))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;7
(= __ (:a {:a 1 :b 2}))
; the converse of example 6
(= 1 (:a {:a 1 :b 2}))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;8
(= __ ({2006 "Torino" 2010 "Vancouver" 2014 "Sochi"} 2010))
; keys need not always be keywords
 (= "Vancouver" ({2006 "Torino" 2010 "Vancouver" 2014 "Sochi"} 2010))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;9
(= __ (get {:a 1 :b 2} :c))
; it is important to know what happens when the value you want
; to search does not exist in the dictionary
; no rocket science here. null/nil were invented for this purpose.
(= nil (get {:a 1 :b 2} :c))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;10
(= __ (get {:a 1 :b 2} :c :key-not-found))
; maps provide a 'default' functionality
; this more like the default on EMIs
; what would you give to the bouncers
; if you don't have money to pay for EMIs
(= :key-not-found (get {:a 1 :b 2} :c :key-not-found))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;11
(= __ (contains? {:a nil :b nil} :b))
; contains? is a predicate and does exactly
; what you might expect it to do.
(= true (contains? {:a nil :b nil} :b))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;12
(= __ (contains? {:a nil :b nil} :c))
; a counter-example of example #11
(= false (contains? {:a nil :b nil} :c))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;13
(= {1 "January" 2 __} (assoc {1 "January" } 2 "February"))
; assoc when applied to a map returns a new map of same type
; assoc when applied to vector returns a new vector
(= {1 "January" 2 "February"} (assoc {1 "January" } 2 "February"))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;14
(= {__ __} (dissoc {1 "January" 2 "February"} 2))
; if you can assoc, you would also want to 'dissoc'
; but you may not want dissoc for vectors
(= {1 "January"} (dissoc {1 "January" 2 "February"} 2))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;15
(= (list __ __ __)
     (sort (keys {2006 "Torino" 2010 "Vancouver" 2014 "Sochi"})))
; this would make the keys sorted
(= (list 2006 2010 2014)
     (sort (keys {2006 "Torino" 2010 "Vancouver" 2014 "Sochi"})))

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;16
(= (list "Sochi" "Torino" __)
     (sort (vals {2006 "Torino" 2010 "Vancouver" 2014 "Sochi"}))))

; and this would be for sorting of values
; the question is kind of dumb, says 3 people A B C ran in a race
; A and B were first and second, who stood third?
(= (list "Sochi" "Torino" "Vancouver")

     (sort (vals {2006 "Torino" 2010 "Vancouver" 2014 "Sochi"})))


No comments:

Post a Comment