Re: [racket-dev] [plt] Push #27454: master branch updated
Is the change to the native-pkgs sha1 intentional? Sam On Sep 8, 2013 3:04 AM, stch...@racket-lang.org wrote: stchang has updated `master' from 672e909880 to 7eaee796e1. http://git.racket-lang.org/plt/672e909880..7eaee796e1 =[ 3 Commits ]== Directory summary: 92.8% pkgs/racket-pkgs/racket-test/tests/racket/ ~~ 060ffeb Stephen Chang stch...@racket-lang.org 2013-09-08 01:48 : | add for/X tests for multi-loop break : M native-pkgs| 2 +- M pkgs/racket-pkgs/racket-test/tests/racket/for.rktl | 6 ++ ~~ b685746 Stephen Chang stch...@racket-lang.org 2013-09-08 02:00 : | add for/X tests for outer-loop #:final condition | | - make sure innermost loop is executed only one more time : M pkgs/racket-pkgs/racket-test/tests/racket/for.rktl | 6 ++ ~~ 7eaee79 Stephen Chang stch...@racket-lang.org 2013-09-08 03:03 : | add more for/X tests | | - #:break and #:final in body with exprs in between | - both #:break and #:final | - skipped #:final : M .../racket-pkgs/racket-test/tests/racket/for.rktl | 25 =[ Overall Diff ]=== native-pkgs ~~~ --- OLD/native-pkgs +++ NEW/native-pkgs @@ -1 +1 @@ -Subproject commit 5f391155f276da25df85081cf8c80a9760a404b0 +Subproject commit f367c0c4b05b91401d68b0180b416d616b31720d pkgs/racket-pkgs/racket-test/tests/racket/for.rktl ~~ --- OLD/pkgs/racket-pkgs/racket-test/tests/racket/for.rktl +++ NEW/pkgs/racket-pkgs/racket-test/tests/racket/for.rktl @@ -383,4 +383,41 @@ (define-sequence-syntax in-X* (lambda () #'in-X) (lambda (stx) #f)) (for/list ([x (in-X* #:x '(1 2 3))]) x))) + +;; extra tests for #:break and #:final +(test '((0 0) (0 1) (1 0) (1 1)) 'multi-level-break + (for*/list ([i 4] [j 2] #:break (= i 2)) (list i j))) +(test '((1 0 0) (1 0 1) (1 1 0) (1 1 1)) 'multi-level-break + (for/list ([i 5] #:when (odd? i) [j 2] #:when #t [k 2] #:break (= i 3)) +(list i j k))) +(test '((0 0) (0 1) (1 0) (1 1) (2 0)) 'outer-loop-final + (for*/list ([i 4][j 2] #:final (= i 2)) (list i j))) +(test '((0 0) (0 1) (1 0) (1 1) (2 0)) 'outer-loop-final + (for/list ([i 4] #:final (= i 2) [j 2]) (list i j))) + +(test '((0 0) (0 1) (1 0) (1 1)) 'break-and-final + (for*/list ([i 4][j 2] #:final (= i 2) #:break (= i 2)) (list i j))) + +(test '((0 0) (0 1) (1 0) (1 1)) 'break-and-final + (for*/list ([i 4][j 2] #:break (= i 2) #:final (= i 2)) (list i j))) + +(test '((0 1) (1 1)) 'skipped-final + (for*/list ([i 4][j 2] #:final (= i 2) #:unless (= j 0)) (list i j))) + +;; check #:break and #:final in body with exprs in between +(test (list 0 1) 'nested-body-break + (for/list ([i 4]) (define j (add1 i)) #:break (= j 3) i)) +(test (list 0 1 2) 'nested-body-final + (for/list ([i 4]) (define j (add1 i)) #:final (= j 3) i)) +(test '((0 0) (0 1) (1 0) (1 1)) 'nested-body-break-and-final + (for*/list ([i 4][j 2]) +(define k i) #:final (= k 2) +(define m i) #:break (= m 2) +(list i j))) +(test '((0 0) (0 1) (1 0) (1 1)) 'nested-body-break-and-final + (for*/list ([i 4][j 2]) +(define m i) #:break (= m 2) +(define k i) #:final (= k 2) +(list i j))) + (report-errs) _ Racket Developers list: http://lists.racket-lang.org/dev
Re: [racket-dev] net/http-client
On Wed, Sep 4, 2013 at 11:03 AM, Jay McCarthy jay.mccar...@gmail.com wrote: On Wed, Aug 28, 2013 at 3:30 PM, Greg Hendershott greghendersh...@gmail.com wrote: This looks great!! A couple suggestions: 1. Support for Expect: 100-continue request headers would be helpful, and I think not too messy to add. The big use case I'm aware of is Amazon S3. If you make a PUT or POST request, it might need to redirect you to another URI (outage, balancing, whatever reason). Expecting and handling 100-continue lets you avoid transmitting potentially large amount of data that would be discarded, and you have to send it all over again in the request to the redirect URI. For (say) a 1 GB upload to S3, this matters. Although I don't know for sure if other upload-ish web APIs offer same, I'd guess some do as this is the use case for 100-continue generally. How I implemented this in my HTTP package was to have a `start-request` function that sends the request line and headers, peeks the response status line, then returns a `boolean?` whether the PUT/POST/PATCH/whatever data should be transmitted. [1] I think your `http-conn-send!` could do similar? Do you think it is appropriate to expect the http-client user to put in the Expect: 100-continue or better to always send it if there is a data component? Great question. I took the approach of requiring the client to supply it if they care. Instead supplying it always/automatically does seem neat. But safe? Reading http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html I'm a little nervous about this section: A server that does not understand or is unable to comply with any of the expectation values in the Expect field of a request MUST respond with appropriate error status. The server MUST respond with a 417 (Expectation Failed) status if any of the expectations cannot be met or, if there are other problems with the request, some other 4xx status. This suggests a scenario where a server might error a request solely because of the presence of an Expect: 100-continue header. That doesn't strike me as reasonable behavior, but I could imagine some server doing it. So I suppose best to default to supplying it automatically, but provide a way for the client to disable that. How to specify disabling? With headers like Server: you have a default but let the user's supplied headers override. But supplying Expect: (i.e. Expect: blank) would feel weird, to a user. And actually sending that -- if it feels weird to a server causing it to error, well that's the whole thing we're trying to avoid, see above. So (tl;dr) perhaps add an optional function parameter that defaults to #t, e.g. `[expect-100-continue? #t]` ? 2. Support for Content-Encoding response headers would also be helpful. Using the same make-pipe approach as you're doing with chunked transfer encoding. [2] Maybe this is mission creep: For HTTP 1.1. you _must_ support Transfer-Encoding: chunked, whereas Content-Encoding is just optional. However it's a good option; using compression can really help out on time as well as bandwidth charges. I just pushed support for this. Nice, thanks! _ Racket Developers list: http://lists.racket-lang.org/dev
Re: [racket-dev] split-for-body from syntax/for-body
On Fri, Sep 6, 2013 at 2:58 PM, Stephen Chang stch...@ccs.neu.edu wrote: It's useful when the condition for loop termination and the value of the loop body both depend on some derived computation from the sequence elements: (for/list ([x (in-stream S)]) (define y (f x)) #:break (g? y) (h y)) Ok I see, thanks. It does make things easier to read when the break expression becomes too large to fit on one line. So is the reason why #:when and #:unless can't be used the same way because there already exist when and unless forms? Are you looking for an equivalent of C's continue statement? I could imagine clauses for skipping to the next iteration using the keyword #:continue or #:next, though I have no idea if the existing loop architecture would easily accommodate them. I don't think calling them #:when or #:unless makes sense outside the for clauses. Carl Eastlund On Fri, Sep 6, 2013 at 2:31 PM, Stephen Chang stch...@ccs.neu.edu wrote: Among the bodys, besides stopping the iteration and preventing later body evaluations, a #:break guard-expr or #:final guard-expr clause starts a new internal-definition context. I had the same thought process as Carl. I now understand the behavior but I don't understand why it's needed? It seems kind of arbitrary since no other form allows multiple internal def contexts in the body like this. Is there a practical example? On Fri, Sep 6, 2013 at 12:58 PM, Carl Eastlund c...@ccs.neu.edu wrote: Okay, I see what's going on here. It's very subtle though, and probably deserves some explanation in split-for-body's documentation. My first thought on seeing my non-fix version break here is that I can make split-for-body break the same way. The problem is that my non-fix separates the definition of fish? from the definitions of red? and blue?, which it depends on. I can make split-for-body separate them the same way, by putting a #:break or #:final clause in between the definition of fish? and the begin form. The problem with doing so is a subtle point about for loops that is only mentioned in the last sentence of the last paragraph of the documentation of for itself: Among the bodys, besides stopping the iteration and preventing later body evaluations, a #:break guard-expr or #:final guard-expr clause starts a new internal-definition context. So that's what split-for-body is preserving, the boundaries between internal definition contexts. That's not at all what I had expected it was doing; I had no idea the body of a for loop constituted multiple such contexts. Anyway, thanks for the clarification, I now understand why abstractions over for loops need to use split-for-body. Carl Eastlund On Fri, Sep 6, 2013 at 12:38 PM, Matthew Flatt mfl...@cs.utah.edu wrote: Sorry that I forgot to add the `let` while turning the code you sent into a full example. Here's another try. #lang racket/base (require (for-syntax racket/base syntax/parse syntax/for-body)) (define-syntax (for/print/good stx) (syntax-parse stx [(_ clauses . body) (with-syntax ([([pre ...] [post ...]) (split-for-body stx #'body)]) (syntax (for clauses pre ... (printf ~v\n (let () post ...)])) (define-syntax-rule (for/print/fixed/not clauses pre ... result) (for clauses pre ... (printf ~v\n (let () result (for/print/fixed/not ([i 1]) (define (fish? v) (or (red? v) (blue? v))) (begin (define (red? v) (eq? v 'red)) (define (blue? v) (eq? v 'blue)) (fish? i))) At Fri, 6 Sep 2013 12:30:17 -0400, Carl Eastlund wrote: You're proving that (let () ...) is necessary, which I have explicitly agreed with since the original email, but you have not yet demonstrated that split-for-body is necessary. Here is the fix I have described twice already, now explicitly put into the define-syntax-rule solution: (define-syntax-rule (for/print/fixed clauses pre .. result) (for clauses pre ... (printf ~v\n (let () result Carl Eastlund On Fri, Sep 6, 2013 at 12:25 PM, Matthew Flatt mfl...@cs.utah.edu wrote: #lang racket/base (require (for-syntax racket/base syntax/parse syntax/for-body)) (define-syntax (for/print/good stx) (syntax-parse stx [(_ clauses . body) (with-syntax ([([pre ...] [post ...]) (split-for-body stx #'body)]) (syntax (for clauses
Re: [racket-dev] [plt] Push #27446: master branch updated
Typed Racket has to expand into code that registers the type of each module-top-level identifier in the global environment so that other modules can find the types to typecheck with. For example, this program: #lang typed/racket (provide x) (define: x : Integer 1) expands into (greatly simplified): #lang ... (#%provide x) (begin-for-syntax (declare #'x Integer-rep)) (define-values (x) 1) but what is `Integer-rep`? It needs to be an expression that _constructs_ the internal Typed Racket representation of the `Integer` type. Previously, that looked something like this: (make-Union (sort (list Negative-Fixnum-rep Positive-Fixnum-rep ...))) and so on and so forth for the components, all the way down to base types. You can imagine how this gets quite large, especially for large types. However, this is wasteful, because every Typed Racket program, at type checking time, defines a constant that's the representation of the `Integer` type, right here [1]. So instead of serializing an expression that constructs the same thing as `-Int`, we can just *reference* `-Int` in the expanded code. To make that possible, Typed Racket now builds a hash table [2] mapping types (really, their representations) to identifiers that denote those types. Then the serializer just consults this table [3]. It turns out that base types (but no others) already used basically this mechanism, by storing the identifier *in* the type representation. But that's now obsolete, and thus was removed in my subsequent commit. As a result, the type serialization is much smaller. [1] https://github.com/plt/racket/blob/master/pkgs/typed-racket-pkgs/typed-racket-lib/typed-racket/types/numeric-tower.rkt#L107 [2] https://github.com/plt/racket/blob/master/pkgs/typed-racket-pkgs/typed-racket-lib/typed-racket/types/base-abbrev.rkt#L23 [3] https://github.com/plt/racket/blob/master/pkgs/typed-racket-pkgs/typed-racket-lib/typed-racket/env/init-envs.rkt#L51 On Sat, Sep 7, 2013 at 3:20 PM, Neil Toronto neil.toro...@gmail.com wrote: On 09/06/2013 04:14 PM, sa...@racket-lang.org wrote: 56b372c Sam Tobin-Hochstadt sa...@racket-lang.org 2013-09-06 14:22 : | Remember types that are defined, and use them in serialization. | | This extends a facility already available for base types, | making that facility no longer strictly needed. | | Shrinks the zo size for the `math` package by almost 1MB. : M .../typed-racket/env/init-envs.rkt| 1 + M .../typed-racket/typecheck/def-export.rkt | 7 +- M .../typed-racket/typecheck/tc-toplevel.rkt| 31 +++--- M .../typed-racket/types/abbrev.rkt | 36 +++ M .../typed-racket/types/base-abbrev.rkt| 12 ++- M .../typed-racket/types/numeric-tower.rkt | 108 +-- Would you mind explaining this a little more? It sounds interesting, and the commit almost has my name in it. :) Neil ⊥ _ Racket Developers list: http://lists.racket-lang.org/dev
Re: [racket-dev] split-for-body from syntax/for-body
So is the reason why #:when and #:unless can't be used the same way because there already exist when and unless forms? Are you looking for an equivalent of C's continue statement? I could imagine clauses for skipping to the next iteration using the keyword #:continue or #:next, though I have no idea if the existing loop architecture would easily accommodate them. I don't think calling them #:when or #:unless makes sense outside the for clauses. Hmm, I take back my previous question, which didn't make sense (because it may result in unwanted voids). Now I'm thinking #:when and #:unless *should* be allowed in the body, for the exact reasons why #:final and #:break are allowed. But presumably there is a reason they were left out? It would be similar to C's continue, but the names should probably be the same, since they do the same thing as clause-based #:when/unless? Yes, I think the current architecture would support this change easily since it's accumulator-based. If a #:when/unless condition is true, you just call the loop with the old accumulators. I can put it in if there is agreement. Carl Eastlund On Fri, Sep 6, 2013 at 2:31 PM, Stephen Chang stch...@ccs.neu.edu wrote: Among the bodys, besides stopping the iteration and preventing later body evaluations, a #:break guard-expr or #:final guard-expr clause starts a new internal-definition context. I had the same thought process as Carl. I now understand the behavior but I don't understand why it's needed? It seems kind of arbitrary since no other form allows multiple internal def contexts in the body like this. Is there a practical example? On Fri, Sep 6, 2013 at 12:58 PM, Carl Eastlund c...@ccs.neu.edu wrote: Okay, I see what's going on here. It's very subtle though, and probably deserves some explanation in split-for-body's documentation. My first thought on seeing my non-fix version break here is that I can make split-for-body break the same way. The problem is that my non-fix separates the definition of fish? from the definitions of red? and blue?, which it depends on. I can make split-for-body separate them the same way, by putting a #:break or #:final clause in between the definition of fish? and the begin form. The problem with doing so is a subtle point about for loops that is only mentioned in the last sentence of the last paragraph of the documentation of for itself: Among the bodys, besides stopping the iteration and preventing later body evaluations, a #:break guard-expr or #:final guard-expr clause starts a new internal-definition context. So that's what split-for-body is preserving, the boundaries between internal definition contexts. That's not at all what I had expected it was doing; I had no idea the body of a for loop constituted multiple such contexts. Anyway, thanks for the clarification, I now understand why abstractions over for loops need to use split-for-body. Carl Eastlund On Fri, Sep 6, 2013 at 12:38 PM, Matthew Flatt mfl...@cs.utah.edu wrote: Sorry that I forgot to add the `let` while turning the code you sent into a full example. Here's another try. #lang racket/base (require (for-syntax racket/base syntax/parse syntax/for-body)) (define-syntax (for/print/good stx) (syntax-parse stx [(_ clauses . body) (with-syntax ([([pre ...] [post ...]) (split-for-body stx #'body)]) (syntax (for clauses pre ... (printf ~v\n (let () post ...)])) (define-syntax-rule (for/print/fixed/not clauses pre ... result) (for clauses pre ... (printf ~v\n (let () result (for/print/fixed/not ([i 1]) (define (fish? v) (or (red? v) (blue? v))) (begin (define (red? v) (eq? v 'red)) (define (blue? v) (eq? v 'blue)) (fish? i))) At Fri, 6 Sep 2013 12:30:17 -0400, Carl Eastlund wrote: You're proving that (let () ...) is necessary, which I have explicitly agreed with since the original email, but you have not yet demonstrated that split-for-body is necessary. Here is the fix I have described twice already, now explicitly put into the define-syntax-rule solution: (define-syntax-rule (for/print/fixed clauses pre .. result) (for clauses pre ... (printf ~v\n (let () result Carl Eastlund On Fri, Sep 6, 2013 at 12:25 PM, Matthew Flatt mfl...@cs.utah.edu wrote: #lang racket/base (require (for-syntax racket/base syntax/parse