私はこれを持っています:
(defn string-> integer [str&[base]] (Integer/parseInt str(if(nil?base)10 base))) (string-> integer "10") (string-> integer "FF" 16)
しかし、これを行うにはより良い方法でなければなりません。
シグネチャのアリティが異なる場合、関数は複数のシグネチャを持つことができます。これを使用して、デフォルト値を提供できます。
_(defn string->integer
([s] (string->integer s 10))
([s base] (Integer/parseInt s base)))
_
false
とnil
が両方とも非値と見なされると仮定すると、_(if (nil? base) 10 base)
_は_(if base base 10)
_、または_(or base 10)
_に短縮できることに注意してください。
Clojure 1.2 [ ref ]以降、rest
引数をマップとして非構造化することもできます。これにより、関数の引数に名前を付けてデフォルトを指定できます。
(defn string->integer [s & {:keys [base] :or {base 10}}]
(Integer/parseInt s base))
今、あなたは電話することができます
(string->integer "11")
=> 11
または
(string->integer "11" :base 8)
=> 9
これは実際に動作していることがわかります: https://github.com/Raynes/clavatar/blob/master/src/clavatar/core.clj (例)
このソリューションは、元のソリューションの精神に近いですが、わずかにきれいです
(defn string->integer [str & [base]]
(Integer/parseInt str (or base 10)))
類似のパターンこれは便利ですor
をlet
と組み合わせて使用します
(defn string->integer [str & [base]]
(let [base (or base 10)]
(Integer/parseInt str base)))
この場合、より冗長ですが、デフォルトは他の入力値に依存にしたい場合に役立ちます。たとえば、次の関数を考えます。
(defn exemplar [a & [b c]]
(let [b (or b 5)
c (or c (* 7 b))]
;; or whatever yer actual code might be...
(println a b c)))
(exemplar 3) => 3 5 35
このアプローチは、named arguments(M. Gilliarのソリューションのように)で動作するように簡単に拡張できます。
(defn exemplar [a & {:keys [b c]}]
(let [b (or b 5)
c (or c (* 7 b))]
(println a b c)))
または、さらに多くの融合を使用します。
(defn exemplar [a & {:keys [b c] :or {b 5}}]
(let [c (or c (* 7 b))]
(println a b c)))
あなたが考慮したいかもしれない別のアプローチがあります: 部分 関数。これらはおそらく、機能のデフォルト値を指定する、より「機能的」で柔軟な方法です。
必要に応じて、主要なパラメーターとしてデフォルトとして提供したいパラメーターを持つ関数を作成することから始めます。
(defn string->integer [base str]
(Integer/parseInt str base))
これは、Clojureのpartial
バージョンでは、関数定義に表示される順序でのみ「デフォルト」値を指定できるためです。パラメータが必要に応じて順序付けされたら、partial
関数を使用して関数の「デフォルト」バージョンを作成できます。
(partial string->integer 10)
この関数を複数回呼び出し可能にするには、def
を使用してvarに入れます。
(def decimal (partial string->integer 10))
(decimal "10")
;10
let
を使用して「ローカルデフォルト」を作成することもできます。
(let [hex (partial string->integer 16)]
(* (hex "FF") (hex "AA")))
;43350
部分関数アプローチには、他の方法よりも1つの重要な利点があります。関数のconsumerは、producer関数の関数定義を変更する必要なし。これはhex
の例で示されており、デフォルト関数decimal
は私が望むものではないと判断しました。
このアプローチのもう1つの利点は、より説明的または異なるスコープ(var、local)である別の名前(10進数、16進数など)をデフォルト関数に割り当てることができることです。必要に応じて、部分関数を上記のアプローチのいくつかと混合することもできます。
(defn string->integer
([s] (string->integer s 10))
([base s] (Integer/parseInt s base)))
(def hex (partial string->integer 16))
(この応答の上部にある理由でパラメーターの順序が逆になっているため、これはブライアンの答えとは少し異なります)