2013-02-22 4 views
5

私はJavaクラスVector2を持っていますが、これはClojureリーダーで「うまくいく」ように説得したいと思います。ClojureプリンタとリーダによるJavaクラスのラウンドトリップ

(def a (vec2 1 2)) 
(print-str a) 
=> "#<Vector2 [1 2]>" 

理想的には、クラスをClojureリーダーが読み取れる形式で印刷したいと思います。すなわち、私は以下を真に戻すことを望みます:

(= a (read-string (print-str a))) 

このラウンドトリップ機能を達成する最良の方法は何ですか?

+0

あなたは私が思う、 'EvalReader'が関与したくないですか? –

+0

@マルコ:提案に開放されています。特に外部APIを意図したものではありません.REPLの利便性と簡単なシリアライズ/デシリアライゼーションのためのものです。 – mikera

+0

私は 'read-eval'を真のままにしておくと、読者は'#=(Vector2.1.2) 'で何をすべきか知っています。 –

答えて

5

クラス/タイプには、print-dupprint-methodマルチメソッドを提供する必要があります。

core.clj

をチェックしてください例:

(import 'java.util.Hashtable) 
(defmethod print-method Hashtable [x writer] 
     (binding [*out* writer] 
     (print (let [h (gensym)] 
       `(let [~h (Hashtable.)] 
        [email protected](map (fn [i] 
           `(.put ~h ~(str "\"" (.getKey i) "\"") ~(.getValue i) )) x) ~h))) )) 
(def a (Hashtable.)) 
(.put a "a" 1) 
(.put a "b" 2) 
(= a (eval (read-string (print-str a)))) 
+0

これは執筆の終わりだけをカバーするようです。それはどのように読書をしますか? –

+0

'read-string'は読み取り用です。基本的に、このマルチメソッドは '(vec2 1 2)'のような文字列形式のs式を返します。実行すると目的のオブジェクトが生成されます – Ankur

+0

これはMikeraが望むものではありません。彼の目的は、彼はネイティブのClojureベクトルのように**読んで**読んでみたいです。 –

関連する問題