我正在尝试Clojure spec并从函数:pre
约束中调用它。
我的规范::mustbe-seql-of-vec-of-2-int
将检查传递给函数的参数是否为从0到4个正好为2个整数的向量的序列:
(require '[clojure.spec.alpha :as s])
(s/def ::mustbe-seql-of-vec-of-2-int
(s/and
::justprint
(s/coll-of
::mustbe-vec-of-2-int
:kind sequential?
:min-count 0
:max-count 4)))
因此,该规范由其他规范组成,尤其是::justprint
,除了打印传递的用于调试的参数和coll-of来测试集合参数之外,什么都不做。
coll-of的文档说:
用法:(按条件排序和选择)
返回满足pred的项目集合的规范。不像 coll-of会完全符合每个值。
但是,作为第一个参数,我没有使用pred(一个接受参数检查并返回真实值的函数),而是另一个规范(一个有参数接受检查并返回的函数)我不确定什么),在这种情况下,该规范是在::mustbe-vec-of-2-int
下注册的。
这非常好用。
这种正确的样式是否可以正常工作?
PS
(s/def ::justprint
#(do
; "vec" to realize the LazySeq, which is not realized by join
(print (d/join [ "::justprint ▶ " (vec %) "\n"] ))
true))
(s/def ::mustbe-vec-of-2-int
(s/coll-of integer? :kind vector? :count 2))
答案 0 :(得分:3)
这是正确的样式并且可以使用吗?
是的。规范,可以解析为规范的关键字以及简单谓词功能可以在clojure.spec API的许多部分中互换使用。在该文档字符串的上下文中,“ Pred”的含义比一般Clojure谓词功能(例如nil?
。
(require '[clojure.spec.alpha :as s])
(s/conform int? 1) ;; => 1
(s/conform int? false) ;; => :clojure.spec.alpha/invalid
s/def
修改clojure.spec注册表,将关键字与spec值相关联。当您将::some-spec-keyword
传递给clojure.spec API时,它将自行从注册表中解析规范值。您还可以“别名”规范,例如(s/def ::foo ::bar)
。
(s/def ::even-int? (s/and int? even?))
(s/conform ::even-int? 2) ;; => 2
(s/conform ::even-int? 3) ;; => :clojure.spec.alpha/invalid
所以这些都是等效的:
(s/conform (s/coll-of (s/and int? even?)) [2 4 6 8])
(s/conform (s/coll-of ::even-int?) [2 4 6 8])
(s/def ::coll-of-even-ints? (s/coll-of ::even-int?))
(s/conform ::coll-of-even-ints? [2 4 6 8])