我在理解delay
宏在Clojure中的工作原理时遇到了一些麻烦。它似乎没有做到期望它做什么(即:延迟评估)。正如您在此代码示例中所看到的那样:
; returns the current time
(defn get-timestamp [] (System/currentTimeMillis))
; var should contain the current timestamp after calling "force"
(def current-time (delay (get-timestamp)))
然而,即使没有使用current-time
宏,在REPL中调用force
似乎会立即评估表达式:
user=> current-time
#<Delay@19b5217: 1276376485859>
user=> (force current-time)
1276376485859
为什么get-timestamp
的评估在第一次force
来电之前没有延迟?
答案 0 :(得分:13)
REPL上出现的各种对象的打印表示是一种称为print-method
的多方法的产物。它驻留在Clojure源代码中的文件core_print.clj
中,它构成了clojure.core
命名空间中的一部分。
这里的问题是对于实现clojure.lang.IDeref
的对象 - deref
/ @
可以操作的Java接口 - print-method
包含对象背后的值在印刷表示中。为此,它需要deref
对象,尽管为打印失败的代理和未决期货做了特殊规定,但总是强制延迟。
实际上我倾向于认为这是一个错误,或者至多是需要改进的情况。作为现在的解决方法,请特别注意不要打印非受迫延误。