The string->number primitive is probably closer to what Jay wants to do.
The only contract I can think of for string->number is ;; Number -> Boolean (define (string->number-able? x) (number? (string->number x))) So the real problem is a performance problem, which a lazy interpretation of contracts by the compiler might be able to eliminate. Is this the true problem Jay -- Matthias On Dec 6, 2010, at 9:45 AM, Robby Findler wrote: > Let's be clear here: our inability to enforce projectionness is in no > way condoning the two coercianlike contracts that you have now > written. > > That said, the only value I see to contracts that only signal errors > (or do nothing) is that programmers know what to expect from them. The > downsides you mention are well taken, of course. > > In this specific case, your message seems slightly confused: certainly > you should be able to use a contract to ensure that the coercion will > always succeed. Let's assume you have done that and now discuss only > where the coercing bit of the "contract" goes. Is it in a higher order > position? Is it something that describes an interface to your module > or can it be considered an internal detail? > > As a possible guide by analogy, consider the path-string? Predicate. > It is the contract on many functions the ultimately is connected to > some kind of a coercion somehwere buried inside the racket primitives > for dealing with the filesystem. Is that like what you want to do? If > so, how would your arguments hold up for that part of our system? > > Robby > > On Monday, December 6, 2010, Jay McCarthy <jay.mccar...@gmail.com> wrote: >> These contracts are not thrown "at dynamic places". The contract is always >> at the module boundary/etc, but its meaning if affected by the dynamic >> context of the particular boundary crossing. [1] >> >> I'm been thinking about why I want to use contracts for this purpose. >> The alternative is to put an any/c contract in all the places I currently >> have response/c and as the first thing in all those functions call >> current-any->response [or as the last thing on returns] on the input >> argument. I would then have to put a note in all the documentation of those >> any/c that it doesn't REALLY accept anything, instead in other accepts >> things that the dynamic current-any->response will turn into a response. If >> the coercion failed, then I would have to throw an error, which be purely >> dynamic with no blame information because it would not be associated with a >> contract boundary. >> >> In contrast, using a contract for this purpose allows me to centralize the >> documentation and behavior of these arguments, get correct blame on places >> where the coercion fails, and abstract the coercion out of the code that is >> using it into its interface. These are all great wins. >> >> In my opinion, if I did not use contracts, the only elegant thing to do >> would be to recreate something almost exactly like the contract system but >> called the coercion system. That is absurd to me when contracts already do >> exactly this. >> >> Am I just not clever enough to think of another elegant way? >> Why is there so much resistance to using the contract system in a perfectly >> legal way according to its own definition & contracts? [2] [i.e. >> "projection" functions are not forced to be projections by any means. / >> contracts already break eq?/equal?-ness / etc] >> >> Jay >> 1. We already have such context-sensitive contracts: >> http://docs.racket-lang.org/xml/index.html#(def._((lib._xml/main..rkt)._permissive/c)) >> >> permissive/c exists to allow DrRacket to embed more snips inside the XML >> boxes, which are otherwise not XML elements. >> 2. make-contract's projection keyword has the contract (-> any/c any/c) >> >> The example of make-contract coerces the procedure by restricting how many >> arguments rather than checking that when it is given that number of >> arguments it is used properly, etc. >> >> Only flat and chaperone contracts attempt to enforce projection-ness. >> On Sun, Dec 5, 2010 at 9:31 AM, Matthias Felleisen <matth...@ccs.neu.edu> >> wrote: >> >> Jay, coercions aka casts in our world are compound words with -> in between >> them. Why do you need a new name? >> >> (There is an inconsistency in their behavior. To wit >> >> Welcome to Racket v5.0.99.4. >>> (integer->char 1000000000000000) >> integer->char: expects argument of type <exact integer in [0,#x10FFFF], not >> in [#xD800,#xDFFF]>; given 1000000000000000 >> >> === context === >> /Users/matthias/plt/collects/racket/private/misc.rkt:78:7 >>> (string->number "a10") >> #f >> >> But that is a historical problem.) >> >> ;; --- >> >> I am also reluctant to throw contracts at dynamic places. Contract >> boundaries should be syntactically distinct, e.g., module boundaries or >> define/contract. >> >> ;; --- >> >> I think you're really just checking an assertion. So perhaps you want to go >> with /a as a suffix. >> >> >> -- Matthias >> >> >> >> >> -- >> Jay McCarthy <j...@cs.byu.edu> >> Assistant Professor / Brigham Young University >> http://faculty.cs.byu.edu/~jay >> >> "The glory of God is Intelligence" - D&C 93 >> >> _________________________________________________ For list-related administrative tasks: http://lists.racket-lang.org/listinfo/dev