我将此(not (some #(= (:length %1) 0) %))
作为后置条件。写得这样很清楚,但是如果不满足这个条件,我就明白了:
Assert failed: (not (some (fn* [p1__17852#] (= (:length p1__17852#) 0)) %))
哪个不太可读。有没有办法为后置条件或前提条件定义消息?
编辑1:
遵循noahlz和noisesmiths建议,(但使用外部命名函数):
(defn not-zero-length
[evseq]
(not (some (fn [item] (= (:length item) 0)) evseq)))
(defn my-func
[evseq]
{:post [(not-zero-length %)]}
evseq)
(my-func '({:length 3}{:length 0}))
给出:
AssertionError Assert failed: (not-zero-length %)
哪个更清楚。
答案 0 :(得分:7)
以下clojure邮件列表thread中讨论了这一点。
查看clojure.core source,您可以看到fn宏只将一个布尔值传递给assert函数,并且不包含用于传递其他消息参数的可选参数。
所以看起来没有办法干净利落地做到这一点。
答案 1 :(得分:3)
同一个帖子中的这个post建议使用clojure.test /是宏,它返回一个有意义的错误消息。
(require '[clojure.test :refer [is]])
(defn get-key [m k]
{:pre [(is (map? m) "m is not a map!")]}
(m k))
(get-key [] 0)
返回
FAIL in clojure.lang.PersistentList$EmptyList@1 (form-init8401797809408331100.clj:2)
m is not a map!
expected: (map? m)
actual: (not (map? []))
AssertionError Assert failed: (is (map? m) "m is not a map!")
答案 2 :(得分:2)
扩展上述建议:
(not (some (fn zero-length [item] (= (:length item) 0)) %))
当您命名匿名函数时,涉及该fn的任何错误都将更具可读性
另外,你上面有两个%的替换是怎么回事? #()不会嵌套。