我在尝试定制函数生成器来支持 spec 教程中描述的情景,但目标是生成的值依赖于具体参数,而不仅仅是 :ret 规范。
在处理这个问题时,我注意到一个奇怪的行为,即在返回之前生成函数被调用21次。
(require '[clojure.spec.alpha :as s]
'[clojure.spec.gen.alpha :as gen])
(s/fdef foo
:args (s/cat :x int?)
:gen #(gen/return
(fn [& argv]
(prn argv)
(gen/generate (s/gen string?)))))
(gen/generate (s/gen `foo))
;; Prints:
;; (-1)
;; (-1)
;; (-2)
;; (-1)
;; (3)
;; (-2)
;; (-2)
;; (-1)
;; (-35)
;; (14)
;; (-16)
;; (26)
;; (-17)
;; (150)
;; (0)
;; (-1)
;; (25)
;; (5638)
;; (543)
;; (57)
;; (257)
;; Returns: #function[fspec-gen-bug.core/fn--6577/fn--6578]
这种行为似乎仅针对函数生成,例如
(s/def ::bar
(s/spec (s/coll-of int?)
:gen #(gen/return
(doto [(gen/generate (s/gen int?))]
prn))))
(gen/generate (s/gen ::bar))
;; Prints:
;; [438803]
;; Returns: [438803]
生成函数被提前调用的好理由是什么?或者这是个bug?