для этого есть две общие функции, связанные, когда вы хотите изменить одно значение, и update-in
, когда вы хотите использовать функцию для изменения значений на основе текущего значения или или хотите изменить несколько значений:
user> (def players {:players
{"p1"
{:id "p1"
:deck []
:hand [{:name "Imp"
:entity-type :card}]
:minions [{:damage-taken 0
:attacks-performed-this-turn 0
:entity-type :minion
:name "Imp"
:id "m1"
:position 0
:owner-id "p1"}]
:hero
{:name "Jaina Proudmoore"
:id "h1"
:entity-type :hero
:mana 0
:damage-taken 0}}}})
#'user/players
В этом случае update-in
- хорошее совпадение, потому что оно позволяет вам делать все, что вы хотите с вложенной коллекцией. Вот пример, который связывает некоторые новые значения, основанные на предыдущих, вы также можете добавить свою функцию для сопоставления здесь ключей.
user> (-> (update-in players [:players "p1" :hero]
#(assoc %
:name (str "long lost twin of " (:name %))
:id "h2"
:entity-type :antihero
:mana (inc (:mana %))
:damage-taken (dec (:damage-taken %))))
clojure.pprint/pprint)
{:players
{"p1"
{:id "p1",
:deck [],
:hand [{:name "Imp", :entity-type :card}],
:minions
[{:damage-taken 0,
:attacks-performed-this-turn 0,
:entity-type :minion,
:name "Imp",
:id "m1",
:position 0,
:owner-id "p1"}],
:hero
{:name "long lost twin of Jaina Proudmoore",
:id "h2",
:entity-type :antihero,
:mana 1,
:damage-taken -1}}}}
user>