[racket] Is this a bug in contracts?

From: Matthias Felleisen (matthias at ccs.neu.edu)
Date: Mon Jan 14 09:27:04 EST 2013

And Harry, do define certain contracts separately, e.g., 

(define shish/c (is-a?/c shish-D%))



On Jan 14, 2013, at 12:24 AM, Asumu Takikawa wrote:

> On 2013-01-13 22:02:44 -0500, Harry Spier wrote:
>> Is this a bug in contracts?  When I ran the following code the
>> contract in onion% didn't give me an error, yet the contract is on an
>> "init sh" but the class doesn't have an "init sh" it has an
>> "init-field sh".  See the line with the comment ;;;;;THIS LINE SHOULD
>> USE init-field not init
> 
> No, this should be correct. An `init` specifies a subset of `init-field`
> (it's not mutually exclusive with it).
> 
>> (define/contract onion%
>>  (class/c [init (sh (is-a?/c shish-D%))]) ;;;;;THIS LINE SHOULD USE init-field not init
>>  (class shish-D% (super-new)
>>    (init-field sh)
>>    (define/override (only-onions?)
>>      (and (send sh only-onions?) #t))))
>> 
>> (send (new onion% [sh (new onion% [sh (new skewer%)])]) only-onions?)
> 
> Notice here that if we change this to:
> 
>  (send (new onion% [sh 5]) only-onions?)
> 
> A contract error is raised appropriately because the init argument was
> wrong, so the contract is clearly protecting the init argument. This is
> the correct behavior, because an `init-field` clause just defines both
> an init argument and a field. The class system doesn't track a separate
> `init-field` thing.  If you only specify the init contract, it only
> protects the init part.
> 
> If you set the field like this:
> 
>  (set-field! sh (new onion% [sh (new onion% [sh (new skewer%)])]) 5)
> 
> It does not raise a contract error. If you want to protect both, you
> either need to revise the contract to
> 
>  (class/c [init-field (sh (is-a?/c shish-D%))])
> 
> or
> 
>  (class/c [init (sh (is-a?/c shish-D%))]
>           [field (sh (is-a?/c shish-D%))])
> 
> Cheers,
> Asumu
> ____________________
>  Racket Users list:
>  http://lists.racket-lang.org/users



Posted on the users mailing list.