[racket] Box: When and why?

From: Greg Hendershott (greghendershott at gmail.com)
Date: Thu Oct 21 17:48:45 EDT 2010

Thank you, I understand now.

It's interesting how little I've need to consider, so far, whether
Racket parameters are call-by-value or call-by-reference.

If you don't use set! on parameters, one reason to consider it
disappears. I've been sticking to a functional style (after an initial
awkward "imperative un-training" period).

Also whenever I've needed to return > 1 value, it's been very natural
to use values (for 2 or 3) or a struct (for more).

On Thu, Oct 21, 2010 at 11:41 AM, Matthias Felleisen
<matthias at ccs.neu.edu> wrote:
>
> Boxes are the closest thing to addresses you can find in Racket.
> You need them when you want to mimic a classical by-reference
> function parameter protocol. For example,
>
>  (define (return-nothing x y z a-box)
>   (set-box! a-box ComputeSomethingWith-x-y-z)
>   (void) ;; just to make clear that nothing else is returned
>   )
>
> You'd call this elsewhere with
>
>  (define my-personal-box (box #f))
>  ...
>  (return-nothing my-personal-box)
>  (unbox my-personal-box)
>
> You can imagine that you have some other ways of referring to
> my-personal-box (say in a list of all your boxes) which you may
> then use to implement other services (saving all boxes to a file).
>
> Some of our old methods that go down to C++ use this protocol.
>
> In your 'p.s.' example, there is no reason whatsoever to
> use a box over set! and variables.
>
> -- Matthias
>
>
>
>
>
> On Oct 21, 2010, at 11:31 AM, Greg Hendershott wrote:
>
>> P.S. Maybe a simpler example I should have used:
>>
>> (define next-web-parameter-id
>>  (let ([i (box 0)])
>>    (lambda ()
>>      (begin0 (unbox i)
>>              (set-box! i (add1 (unbox i)))))))
>>
>> In both examples the box is involved in a closure lambda pattern.
>>
>> This example, my old C/C++ brain wants to interpret it as a kind of
>> thread-safe increment of a variable. But what's really going on?
>>
>> On Thu, Oct 21, 2010 at 11:22 AM, Greg Hendershott
>> <greghendershott at gmail.com> wrote:
>>> Where can I find more information about the use scenarios for "box"?
>>>
>>> The Guide is terse:
>>>
>>>>>
>>> 3.11 Boxes
>>>
>>> A box is like a single-element vector. It can print as a quoted #&
>>> followed by the printed form of the boxed value. A #& form can also be
>>> used as an expression, but since the resulting box is constant, it has
>>> practically no use.
>>> <<
>>>
>>> This explains what a box is, but not why or when you would want to use one.
>>>
>>> I see box used as in this example from servlet-dispatch.rkt:
>>>
>>> (define (dispatch/servlet
>>> ...
>>>  (define servlet-box (box #f))
>>> ...
>>>  (filter:make
>>> ...
>>>    (lambda (url)
>>>      (or (unbox servlet-box)
>>>          (let ([servlet
>>>                 (parameterize ([current-custodian (make-custodian)]
>>>                                [current-namespace
>>>                                 (make-servlet-namespace
>>>                                  #:additional-specs
>>>                                  default-module-specs)])
>>>                   (if stateless?
>>>                       (make-stateless.servlet
>>> servlet-current-directory stuffer manager start)
>>>                       (make-v2.servlet servlet-current-directory
>>> manager start)))])
>>>            (set-box! servlet-box servlet)
>>>            servlet))))))
>>>
>>> And I'm scratching my head, not understanding the point of using a box
>>> as opposed to a simple non-boxed value.
>>>
>>> My question isn't about this code per se; only an example. Generally,
>>> in what situations would you use a box, and why?
>>>
>>> Thank you.
>>>
>> _________________________________________________
>>  For list-related administrative tasks:
>>  http://lists.racket-lang.org/listinfo/users
>
>


Posted on the users mailing list.