サーチ…


ベクトルを破壊する

ベクトルの構造を解除する方法は次のとおりです。

(def my-vec [1 2 3])

次に、たとえばletブロック内で、次のようにベクトルから非常に簡単に値を抽出できます。

(let [[x y] my-vec]
 (println "first element:" x ", second element: " y))
;; first element: 1 , second element: 2

地図を破壊する

マップの構造を解除する方法は次のとおりです。

(def my-map {:a 1 :b 2 :c 3})

次に、たとえばletブロック内で、次のようにマップから非常に簡単に値を抽出できます。

(let [{x :a y :c} my-map]
  (println ":a val:" x ", :c val: " y))
;; :a val: 1 , :c val: 3

各マッピングで抽出された値は左側にあり、関連付けられているキーは右側にあることに注意してください。

キーと同じ名前のバインディングに値をデストラクションする場合は、このショートカットを使用できます。

(let [{:keys [a c]} my-map]
  (println ":a val:" a ", :c val: " c))
;; :a val: 1 , :c val: 3

キーが文字列の場合は、ほぼ同じ構造を使用できます。

(let [{:strs [foo bar]} {"foo" 1 "bar" 2}]
  (println "FOO:" foo  "BAR: " bar ))
;; FOO: 1 BAR: 2

記号についても同様です。

(let [{:syms [foo bar]} {'foo 1 'bar 2}]
  (println "FOO:" foo "BAR:" bar))
;; FOO: 1 BAR: 2

ネストされたマップの構造を解除する場合は、上で説明したバインディングフォームをネストできます。

(def data
  {:foo {:a 1
         :b 2}
   :bar {:a 10
         :b 20}})

(let [{{:keys [a b]} :foo
       {a2 :a b2 :b} :bar} data]
  [a b a2 b2])
;; => [1 2 10 20]

残りの要素をシーケンスに分解する

次のようなベクトルがあるとしましょう:

(def my-vec [1 2 3 4 5 6])

最初の3つの要素を抽出し、残りの要素をシーケンスとして取得したいとします。これは次のようにして行うことができます。

(let [[x y z & remaining] my-vec]
 (println "first:" x ", second:" y "third:" z "rest:" remaining))
;= first: 1 , second: 2 third: 3 rest: (4 5 6)

入れ子にされたベクトルの破壊

入れ子にされたベクトルを分解することができます:

(def my-vec [[1 2] [3 4]])

(let [[[a b][c d]] my-vec]
  (println a b c d))
;; 1 2 3 4

デフォルト値を使用してマップを破棄する

マップ内に存在しない可能性があるマップの下でキーを破棄したいが、非構造化値のデフォルト値が必要な場合があります。あなたはこうすることができます:

(def my-map {:a 3 :b 4})
(let [{a :a
       b :b
       :keys [c d]
       :or {a 1
            c 2}} my-map]
  (println a b c d))
  ;= 3 4 2 nil

fnのパラメータを破壊する

Destructurlingは、fnのparamリストと同様に、多くの場所で動作します。

(defn my-func [[_ a b]]
  (+ a b))

(my-func [1 2 3]) ;= 5
(my-func (range 5)) ;= 3

破壊はparamリストの& rest構文のためにも機能します:

(defn my-func2 [& [_ a b]]
  (+ a b))

(my-func2 1 2 3) ;= 5
(apply my-func2 (range 5)) ;= 3

残りのシーケンスをマップに変換する

デストラクタリングでは、シーケンスをマップとして解釈することもできます。

(def my-vec [:a 1 :b 2])
(def my-lst '("smthg else" :c 3 :d 4))

(let [[& {:keys [a b]}] my-vec
      [s & {:keys [c d]} my-lst]
  (+ a b c d)) ;= 10

名前付きパラメータで関数を定義すると便利です:

(defn my-func [a b & {:keys [c d] :or {c 3 d 4}}]
  (println a b c d))

(my-func 1 2) ;= 1 2 3 4
(my-func 3 4 :c 5 :d 6) ;= 3 4 5 6

概要

Destructuringを使用すると、さまざまなオブジェクトから別の変数にデータを抽出できます。以下の各例では、各変数はそれ自身の文字列に割り当てられます( a = "a" 、b = "b" 、&​​c)。

タイプ data / コメントの価値
vec (let [[abc] data ...) ["a" "b" "c"]
ネストされたvec (let [[[ab] [cd]] data ...) [["a" "b"] ["c" "d"]]
map (let [{a :ab :bc :c} data ...) {:a "a" :b "b" :c "c"}
- 代替: (let [{:keys [abc]} data ...) キーの後に変数名が付けられたとき。

ヒント:

キーの名前を破壊してバインドする

場合によっては、マップの構造を解除するときに、構造化された値をそれぞれのキー名にバインドしたいことがあります。データ構造の細かさに応じて、 標準の構造スキームを使用することは少し冗長かもしれません。

たとえば、次のようなマップベースのレコードがあります。

(def john {:lastname "McCarthy" :firstname "John" :country "USA"})

我々は通常次のようにそれを破棄する:

(let [{lastname :lastname firstname :firstname country :country} john]
    (str firstname " " lastname ", " country))
;;"John McCarthy, USA"

ここでは、データ構造は3つのスロット(名字、姓、国 )で非常に単純ですが、もっと細かいデータ構造(3よりも多くのスロットを持つ)ですべてのキー名を2回繰り返さなければならない場合、 。

代わりに、これを処理するより良い方法は:keys (ここでキーはキーワードです)とバインドしたいキー名を選択することです:

(let [{:keys [firstname lastname country]} john]
    (str firstname " " lastname ", " country))
;;"John McCarthy, USA"

同じ直感的なロジックが、 シンボル:symsを使用)と普通の古い文字列:strsを使用)のような他のキータイプにも適用されます。

;; using strings as keys
(def john {"lastname" "McCarthy" "firstname" "John" "country" "USA"})
;;#'user/john

;; destructuring string-keyed map
(let [{:strs [lastname firstname country]} john]
    (str firstname " " lastname ", " country))
;;"John McCarthy, USA"

;; using symbols as keys
(def john {'lastname "McCarthy" 'firstname "John" 'country "USA"})

;; destructuring symbol-keyed map
(let [{:syms [lastname firstname country]} john]
    (str firstname " " lastname ", " country))
;;"John McCarthy, USA"

元の引数の値を破壊して名前を付ける

(defn print-some-items 
   [[a b :as xs]]
  (println a)
  (println b)
  (println xs))

(print-some-items [2 3])

この例では、出力

2
3
[2 3]

引数が破壊され、アイテム23がシンボルab割り当てられます。オリジナルの引数、ベクトル全体[2 3]もシンボルxs割り当てられます。



Modified text is an extract of the original Stack Overflow Documentation
ライセンスを受けた CC BY-SA 3.0
所属していない Stack Overflow