Featured post
What is the idiomatic way to assoc several keys/values in a nested map in Clojure? -
imagine have map this:
(def person { :name { :first-name "john" :middle-name "michael" :last-name "smith" }})
what idiomatic way change values associated both :first-name , :last-name in 1 expression?
(clarification: let's want set :first-name "bob" , :last-name "doe". let's map has other values in want preserve, constructing scratch not option)
here couple of ways.
user> (update-in person [:name] assoc :first-name "bob" :last-name "doe") {:name {:middle-name "michael", :last-name "doe", :first-name "bob"}} user> (update-in person [:name] merge {:first-name "bob" :last-name "doe"}) {:name {:middle-name "michael", :last-name "doe", :first-name "bob"}} user> (update-in person [:name] {:first-name "bob" :last-name "doe"}) {:name {:middle-name "michael", :last-name "doe", :first-name "bob"}} user> (-> person (assoc-in [:name :first-name] "bob") (assoc-in [:name :last-name] "doe")) {:name {:middle-name "michael", :last-name "doe", :first-name "bob"}}
edit
update-in
recursive assoc
s on map. in case it's equivalent to:
user> (assoc person :name (assoc (:name person) :first-name "bob" :last-name "doe"))
the repetition of keys becomes more , more tedious go deeper series of nested maps. update-in
's recursion lets avoid repeating keys (e.g. :name
) on , over; intermediary results stored on stack between recursive calls. take @ source update-in see how it's done.
user> (def foo {:bar {:baz {:quux 123}}}) #'user/foo user> (assoc foo :bar (assoc (:bar foo) :baz (assoc (:baz (:bar foo)) :quux (inc (:quux (:baz (:bar foo))))))) {:bar {:baz {:quux 124}}} user> (update-in foo [:bar :baz :quux] inc) {:bar {:baz {:quux 124}}}
assoc
dynamic (as update-in
, assoc-in
, , other clojure functions operate on clojure data structures). if assoc
onto map, returns map. if assoc
onto vector, returns vector. @ source assoc , take in in rt.java
in clojure source details.
- Get link
- X
- Other Apps
Comments
Post a Comment