我想从Clojure写出EDN数据文件作为标记文字。尽管clojure.edn API包含readread-string,但没有编写器。我熟悉报告here的问题。基于此,据我了解,prpr-str函数是今天要使用的功能。

我想与StackOverflow社区进行检查,看看是否可以将如下所示的方式视为写出EDN文件的“正确”方法:

(spit "friends.edn" (apply str
  (interpose "\n\n"
             [(pr-str (symbol "#address-book/person") {:name "Janet Wood"})
              (pr-str (symbol "#address-book/person") {:name "Jack Tripper"})
              (pr-str (symbol "#address-book/person") {:name "Chrissy Snow"})])))


如果在生产中使用EDN,如何写出EDN文件?与上述类似?我有什么需要注意的问题吗?

更新资料

Clojure Cookbook条目"Emitting Records as EDN Values"包含对该问题的更详尽说明以及导致有效EDN标记的处理方法。

最佳答案

您无需手动生成标签。如果使用任何clojure类型定义机制,它们将由打印机创建。 defrecord为此特别方便。

(ns address-book)
(defrecord person [name])

(def people [(person. "Janet Wood")
             (person. "Jack Tripper")
             (person. "Chrissy Snow")])

address-book> (pr-str people)
"[#address_book.person{:name \"Janet Wood\"}
  #address_book.person{:name \"Jack Tripper\"}
  #address_book.person{:name \"Chrissy Snow\"}]"


如果希望它们格式化得更好,可以将with-out-strclojure.pprint/pprint组合在一起。使用Clojure类型创建标签还可以使您免费阅读这些标签。

address-book> (read-string (pr-str people))
[#address_book.person{:name "Janet Wood"}
 #address_book.person{:name "Jack Tripper"}
 #address_book.person{:name "Chrissy Snow"}]

address-book> (def read-people (read-string (pr-str people)))
#'address-book/read-people

address-book> (type (first read-people))
address_book.person


我看到的唯一缺点是,如果名称中包含-,则会失去对标记外观的控制,因为Java类无法包含这些标记,因此它们会转换为下划线。

10-05 23:16