如何以#inst打印时间

时间:2013-07-09 17:29:39

标签: clojure

很容易阅读日期文字:

(read-string "#inst \"2012\"")
        ;;; ⇒ #inst "2012-01-01T00:00:00.000-00:00"

如何将日期输出为#inst...字面值?

这不起作用:

(pr-str (clj-time.core/now))
        ;;; ⇒ "#<DateTime 2013-07-09T17:26:30.058Z>"

(read-string (pr-str (clj-time.core/now)))
        ;;; ⇒ <err>
        ;;;   RuntimeException Unreadable form  clojure.lang.Util.runtimeException (Util.java:219)

1 个答案:

答案 0 :(得分:11)

当您读入#inst字面值时,默认情况下会创建java.util.Date个实例。这些方法在print-method命名空间(1.5.1源的相关片段为here)中为clojure.instant(负责对象的打印表示的多方法)定义了一种方法。

clj-time使用Joda-Time中的DateTime类型,该类型没有设置自定义print-method方法。这是有道理的,因为产生一个不会往返的表示的print-method很少是可取的。为了使其往返,您必须使用非标准的#inst读者。为实现这一目标,如果您正在阅读edn数据,则可以使用clojure.edn/read(或read-string)传递相应的阅读器,如文档字符串中所述:

(require '[clojure.edn :as edn])

(edn/read {:readers {'inst your-inst-reader}} rdr)

使用clj-time时,your-inst-reader将类似于#(clj-time.format/parse some-formatter %)。然后,您可以按照print-method的示例提供匹配的clojure.instant定义。 (或者你可以提供print-method定义并记住你不会得到完美的往返; clj-time提供非常方便的强制函数 - 见下文 - 所以这可能没问题。)

或者,您可以打印并阅读java.util.Date个实例,并将它们转换为DateTime个;在clj-time.coerce中有执行此操作的功能。