Re: Help with using spec

2016-10-18 Thread 'Jason Courcoux' via Clojure
Hi Alex,

Thanks very much for this, makes sense and has solved my issue.

After a trying a few things, it appears that the ArityException was thrown
because I would have needed to wrap my regex with s/spec

i,e,

(s/fdef my-function :args (s/cat :board (s/spec ::board)))

So I think this all makes sense now.

Thanks again.

Jason



On 17 October 2016 at 21:02, Alex Miller  wrote:

> I would back way up to the beginning and reconsider your ::board spec.
> Generally for any data where the structures are homogenous, you're probably
> better off using one of the collection specs like coll-of (or map-of,
> every, every-kv) rather than a regex, which should primarily be used when
> you have a sequential structure with syntactic "parts" to it (such as an
> arg string or other "dsl" type use case).
>
> Because s/and flows conformed values you can get the same effect as you
> did with &:
>
> (s/def ::board (s/and (s/coll-of ::row :min-count 1) #(apply = (map count
> %
>
> Your generator seems like it should work. You might also want to constrain
> more tightly than pos-int? to keep it from getting out of hand. You could
> use something like (s/gen (s/int-in 1 10)) for example.
>
>
>
> On Monday, October 17, 2016 at 2:32:20 PM UTC-5, Jason Courcoux wrote:
>>
>> Hi.
>>
>> I've been experimenting with clojure spec and a game of life problem, and
>> have been trying to spec a rectangular board of unknown size made up of a
>> collection of rows, each of which contain an equal number of cells. My
>> initial attempt was:-
>>
>> (def cell? #{0 1})
>>
>> (s/def ::row (s/coll-of cell? :min-count 1))
>>
>> (s/def ::board (s/& (s/+ ::row)
>> #(apply = (map count %
>>
>>
>> This appears to work, but I'm wondering if there is a better way to
>> specify the constraint that every row should be the same length? What would
>> be the recommended way to achieve this?
>>
>> Following on from this, I then wanted to generate input boards and
>> exercise a function so I tried the following which give me an
>> ArityException:-
>>
>> (s/def ::board (s/with-gen
>>  (s/& (s/+ ::row)
>>   #(apply = (map count %)))
>>  #(gen/bind (s/gen pos-int?)
>> (fn [n]
>>   (s/gen (s/coll-of (s/coll-of cell? :count 
>> n)))
>>
>> (s/fdef my-function :args (s/cat :board ::board))
>>
>> (defn my-function [board])
>>
>> (s/exercise (:args (s/get-spec `my-function)) 1)
>>
>> => ([([1] [0] [0] [1] [0]) {:board [[1] [0] [0] [1] [0]]}])
>>
>> (s/exercise-fn `my-function)
>>
>> => ArityException Wrong number of args (20) passed to: user/my-function
>>
>>
> This is pretty interesting and the number 20 is pretty suspicious as
> that's the max number of args per function - I'm guessing pos-int? is
> causing problems there.
>
>
>>
>>
>> If I try and do something similar without the custom generator such as:
>>
>> (s/def ::coll (s/coll-of (s/coll-of int? :count 2)))
>>
>> (s/fdef my-function2 :args (s/cat :board ::coll))
>>
>> (defn my-function2 [board])
>>
>> (s/exercise (:args (s/get-spec `my-function2)) 1)
>>
>> => ([(*[*[0 -1] [0 -1] [0 -1]*]*) {:board [[0 -1] [0 -1] [0 -1]]}])
>>
>> (s/exercise-fn `my-function2)
>>
>> This all works as expected. I can see that there is an extra level of
>> nesting here though and this must be where the error is coming from, as
>> it's applying my-function to the collection rather than using it as a
>> single argument - but I'm not sure what is causing this difference.
>>
>> These look the same in terms of structure:
>>
>> (gen/sample (s/gen ::coll) 1)
>> => ([[-1 -1] [-1 0] [0 -1] [-1 -1] [-1 0] [-1 0]])
>>
>> (gen/sample (s/gen ::board) 1)
>> => ([[0 1] [1 1] [1 1] [1 1] [1 1] [0 0] [0 1]])
>>
>> (s/fdef my-function :args (s/cat :board ::board))
>>
>> (s/fdef my-function2 :args (s/cat :board ::coll))
>>
>>
>> But these don't:
>>
>> (gen/sample (s/gen (:args (s/get-spec `my-function))) 1)
>> => (([1 0] [0 0] [0 1] [0 1] [1 1]))
>> (gen/sample (s/gen (:args (s/get-spec `my-function2))) 1)
>> => (([[-1 -1] [-1 -1] [0 0] [0 0] [-1 0] [-1 -1] [0 0]]))
>>
>>
>> I'm sure it's something obvious, but I been looking for a couple of hours
>> and can't seem to see it - could someone please help point me in the right
>> direction.
>>
>> Thanks in advance.
>>
>> Jason
>>
>>
>> --
>> Jason Courcoux
>>
> --
> You received this message because you are subscribed to the Google
> Groups "Clojure" group.
> To post to this group, send email to clojure@googlegroups.com
> Note that posts from new members are moderated - please be patient with
> your first post.
> To unsubscribe from this group, send email to
> clojure+unsubscr...@googlegroups.com
> For more options, visit this group at
> http://groups.google.com/group/clojure?hl=en
> ---
> You received this message because you are subscribed to the Google Groups
> "Clojure" group.
> To unsubscribe from this group and stop receiving emails 

Re: Help with using spec

2016-10-17 Thread Alex Miller
I would back way up to the beginning and reconsider your ::board spec. 
Generally for any data where the structures are homogenous, you're probably 
better off using one of the collection specs like coll-of (or map-of, 
every, every-kv) rather than a regex, which should primarily be used when 
you have a sequential structure with syntactic "parts" to it (such as an 
arg string or other "dsl" type use case).

Because s/and flows conformed values you can get the same effect as you did 
with &:

(s/def ::board (s/and (s/coll-of ::row :min-count 1) #(apply = (map count 
%

Your generator seems like it should work. You might also want to constrain 
more tightly than pos-int? to keep it from getting out of hand. You could 
use something like (s/gen (s/int-in 1 10)) for example.



On Monday, October 17, 2016 at 2:32:20 PM UTC-5, Jason Courcoux wrote:
>
> Hi.
>
> I've been experimenting with clojure spec and a game of life problem, and 
> have been trying to spec a rectangular board of unknown size made up of a 
> collection of rows, each of which contain an equal number of cells. My 
> initial attempt was:-
>
> (def cell? #{0 1})
>
> (s/def ::row (s/coll-of cell? :min-count 1))
>
> (s/def ::board (s/& (s/+ ::row)
> #(apply = (map count %
>
>
> This appears to work, but I'm wondering if there is a better way to 
> specify the constraint that every row should be the same length? What would 
> be the recommended way to achieve this?
>
> Following on from this, I then wanted to generate input boards and 
> exercise a function so I tried the following which give me an 
> ArityException:-
>
> (s/def ::board (s/with-gen
>  (s/& (s/+ ::row)
>   #(apply = (map count %)))
>  #(gen/bind (s/gen pos-int?)
> (fn [n]
>   (s/gen (s/coll-of (s/coll-of cell? :count 
> n)))
>
> (s/fdef my-function :args (s/cat :board ::board))
>
> (defn my-function [board])
>
> (s/exercise (:args (s/get-spec `my-function)) 1)
>
> => ([([1] [0] [0] [1] [0]) {:board [[1] [0] [0] [1] [0]]}])
>
> (s/exercise-fn `my-function)
>
> => ArityException Wrong number of args (20) passed to: user/my-function
>
>
This is pretty interesting and the number 20 is pretty suspicious as that's 
the max number of args per function - I'm guessing pos-int? is causing 
problems there.
 

>
>
> If I try and do something similar without the custom generator such as:
>
> (s/def ::coll (s/coll-of (s/coll-of int? :count 2)))
>
> (s/fdef my-function2 :args (s/cat :board ::coll))
>
> (defn my-function2 [board])
>
> (s/exercise (:args (s/get-spec `my-function2)) 1)
>
> => ([(*[*[0 -1] [0 -1] [0 -1]*]*) {:board [[0 -1] [0 -1] [0 -1]]}])
>
> (s/exercise-fn `my-function2)
>
> This all works as expected. I can see that there is an extra level of 
> nesting here though and this must be where the error is coming from, as 
> it's applying my-function to the collection rather than using it as a 
> single argument - but I'm not sure what is causing this difference. 
>
> These look the same in terms of structure:
>
> (gen/sample (s/gen ::coll) 1)
> => ([[-1 -1] [-1 0] [0 -1] [-1 -1] [-1 0] [-1 0]])
>
> (gen/sample (s/gen ::board) 1)
> => ([[0 1] [1 1] [1 1] [1 1] [1 1] [0 0] [0 1]])
>
> (s/fdef my-function :args (s/cat :board ::board))
>
> (s/fdef my-function2 :args (s/cat :board ::coll))
>
>
> But these don't:
>
> (gen/sample (s/gen (:args (s/get-spec `my-function))) 1)
> => (([1 0] [0 0] [0 1] [0 1] [1 1]))
> (gen/sample (s/gen (:args (s/get-spec `my-function2))) 1)
> => (([[-1 -1] [-1 -1] [0 0] [0 0] [-1 0] [-1 -1] [0 0]]))
>
>
> I'm sure it's something obvious, but I been looking for a couple of hours 
> and can't seem to see it - could someone please help point me in the right 
> direction.
>
> Thanks in advance.
>
> Jason
>
>
> -- 
> Jason Courcoux
>

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Help with using spec

2016-10-17 Thread 'Jason Courcoux' via Clojure
Hi.

I've been experimenting with clojure spec and a game of life problem, and
have been trying to spec a rectangular board of unknown size made up of a
collection of rows, each of which contain an equal number of cells. My
initial attempt was:-

(def cell? #{0 1})

(s/def ::row (s/coll-of cell? :min-count 1))

(s/def ::board (s/& (s/+ ::row)
#(apply = (map count %


This appears to work, but I'm wondering if there is a better way to specify
the constraint that every row should be the same length? What would be the
recommended way to achieve this?

Following on from this, I then wanted to generate input boards and exercise
a function so I tried the following which give me an ArityException:-

(s/def ::board (s/with-gen
 (s/& (s/+ ::row)
  #(apply = (map count %)))
 #(gen/bind (s/gen pos-int?)
(fn [n]
  (s/gen (s/coll-of (s/coll-of cell? :count n)))

(s/fdef my-function :args (s/cat :board ::board))

(defn my-function [board])

(s/exercise (:args (s/get-spec `my-function)) 1)

=> ([([1] [0] [0] [1] [0]) {:board [[1] [0] [0] [1] [0]]}])

(s/exercise-fn `my-function)

=> ArityException Wrong number of args (20) passed to: user/my-function



If I try and do something similar without the custom generator such as:

(s/def ::coll (s/coll-of (s/coll-of int? :count 2)))

(s/fdef my-function2 :args (s/cat :board ::coll))

(defn my-function2 [board])

(s/exercise (:args (s/get-spec `my-function2)) 1)

=> ([(*[*[0 -1] [0 -1] [0 -1]*]*) {:board [[0 -1] [0 -1] [0 -1]]}])

(s/exercise-fn `my-function2)

This all works as expected. I can see that there is an extra level of
nesting here though and this must be where the error is coming from, as
it's applying my-function to the collection rather than using it as a
single argument - but I'm not sure what is causing this difference.

These look the same in terms of structure:

(gen/sample (s/gen ::coll) 1)
=> ([[-1 -1] [-1 0] [0 -1] [-1 -1] [-1 0] [-1 0]])

(gen/sample (s/gen ::board) 1)
=> ([[0 1] [1 1] [1 1] [1 1] [1 1] [0 0] [0 1]])

(s/fdef my-function :args (s/cat :board ::board))

(s/fdef my-function2 :args (s/cat :board ::coll))


But these don't:

(gen/sample (s/gen (:args (s/get-spec `my-function))) 1)
=> (([1 0] [0 0] [0 1] [0 1] [1 1]))
(gen/sample (s/gen (:args (s/get-spec `my-function2))) 1)
=> (([[-1 -1] [-1 -1] [0 0] [0 0] [-1 0] [-1 -1] [0 0]]))


I'm sure it's something obvious, but I been looking for a couple of hours
and can't seem to see it - could someone please help point me in the right
direction.

Thanks in advance.

Jason


-- 
Jason Courcoux

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.