clojure-spec

About: http://clojure.org/about/spec Guide: http://clojure.org/guides/spec API: https://clojure.github.io/spec.alpha/clojure.spec.alpha-api.html
ataggart 2020-03-10T12:06:31.119600Z

Anyone have insight into why the such-that is used here? https://github.com/clojure/spec.alpha/blob/spec.alpha-0.2.176/src/main/clojure/clojure/spec/gen/alpha.clj#L187

ataggart 2020-03-10T12:09:11.120400Z

Our tests are occationally failing with "Couldn't satisfy such-that predicate after 10 tries.", and the associated pred is :pred #object[clojure.core$ratio_QMARK_ 0x62fb2f00 "clojure.core$ratio_QMARK_@62fb2f00"].

2020-03-10T12:13:10.120600Z

there is some mention of such-that failures in gary fredericks' generators video at around 16:16 -- https://www.youtube.com/watch?v=F4VZPxLZUdA

2020-03-10T12:25:54.126200Z

ratios are conceptually goofy because you may or may not want to consider integers to be ratios in a given context it's useful to think of integers as special kinds of ratios, because almost any use case for ratios should almost certainly apply to integers as well. It's hard to do arithmetic with ratios without bumping into integers inadvertently at least (e.g., (* 3/4 4/3)) but arguably it would surprise people if (ratio? 42) returned true, so it doesn't; maybe there are other good reasons for this too beyond just surprise in any case, there's a mismatch because test.check takes the first approach, but ratio? wearing its spec hat obviously has the same semantics as ratio? wearing its predicate hat, and so when you generate from it you don't want to generate integers I think (such-that ratio? (ratio)) could definitely be improved; setting a higher retry threshold would stop the exceptions, but a custom generator would be the best; something like (gen/let [[n d] (gen/tuple gen/large-integer gen/large-integer)] (let [r (/ n d)] (if (ratio? r) r (/ (inc n) d)))) there might be some arithmetical edge case there I'm not thinking of, but I think that works

2020-03-10T12:27:07.126600Z

also I forgot to handle (zero? d)

ataggart 2020-03-10T13:25:11.126700Z

Thanks for that! I thought I was losing my mind.

ataggart 2020-03-10T13:28:09.126900Z

Perhaps spec'ing on rational? is the way I should go.