コードをデータとして扱う練習として、私はClojureコードをとり、foo
呼び出しのすべてのbar
呼び出しを変更したいと考えました。しかし、私は機能の平等をチェックするのに苦労しました。私の問題は次のとおりです。Clojure関数の等価性を名前で確認する
(= foo foo) ;returns true
(= foo (first `(foo))) ;returns false
2番目の同等性をチェックする適切な方法は何ですか?
コードをデータとして扱う練習として、私はClojureコードをとり、foo
呼び出しのすべてのbar
呼び出しを変更したいと考えました。しかし、私は機能の平等をチェックするのに苦労しました。私の問題は次のとおりです。Clojure関数の等価性を名前で確認する
(= foo foo) ;returns true
(= foo (first `(foo))) ;returns false
2番目の同等性をチェックする適切な方法は何ですか?
理由は、あなたがリストを引用ということです:彼らは自動的に変数置換を行います。
> (= 'foo (first '(foo)))
true
> (= 'foo (first (list foo)))
false
> (= foo (first (list foo)))
true
答えは、Clojureの中のシンボルが特別であるということです。あなたの元の問題は、キーワードや文字列を使用していた場合
、それは完全に働いているだろう:私たちは、「関数呼び出し」のそれのデフォルトの意味をオフにするには、リストを引用する必要が
(= "foo" (first ["foo"]))) => true
(= :foo (first [:foo ]))) => true
(= "foo" (first '("foo")))) => true
(= :foo (first '(:foo)))) => true
注意してください。我々はデータの一部としてシンボルdoh
を扱いたい場合は、我々はデフォルトの動作をオフにするには、それを引用する必要が
(def doh 5)
(= 5 doh) => true
:
同様に、記号は「変数置換」のデフォルトの解釈を持っています:
(= (symbol "doh") 'doh) => true
注:一重引用符を使用すると、引用符付きのフォーム内のすべてを再帰的に引用します。 symbol
機能が変換されますことを
(= 'foo (first '(foo))) => true
(= (symbol "foo") (first '(foo))) => true
注:それは我々がターンオフすることができ、「ファンクションコール」括弧と一つだけの単一引用符のシンボルの「変数置換」行動の行動を意味し、通常の文字列をシンボルに変換します。
最後に、単一引用符文字がquote
の名前の「機能」のためのthe Clojure Readerでただのショートカットであることに注意してください。
(= (quote foo) (first '(foo))) => true
quote
は実際に特殊な形、関数ではなく。これはコンパイラに組み込まれており、関数の通常の規則に従わないことを意味します。それ以外の場合は、自動的に変数置換を行っているだろうし、上記のように見えただろう:(quote 5)
と5
は、両方のコンパイラに同じであることを
(= (quote 5) (first '(foo))) => false
注意。整数5
は、記号foo
を含む長さ1のリストの最初の項目と等しくないため、式はfalseです。