1

I am reading the book Scheme and the Art of Programming, but cannot think of an answer to the following question:

If r is

(escaper (lambda (continuation) (continuation body))

in (... (call/cc r) ...), when can r be rewritten as

(lambda (continuation) body)
Will Ness
  • 62,652
  • 8
  • 86
  • 167
Lucas
  • 145
  • 1
  • 7
  • `escaper` is not part of Scheme. it is defined by that book, *Scheme and the Art of Programming*, so it is important to mention it. *" `escaper` turns its argument procedure into similarly defined 'escape' procedure (a.k.a. 'continuation'), which, when invoked, its result becomes the result of the entire computation. Anything awaiting the result [of that escape procedure's invocation] is ignored."* (slightly copy-edited) – Will Ness Apr 27 '20 at 13:06
  • `(call/cc r)` can appear anywhere in that expression. that's what `... ...` signify. – Will Ness Apr 27 '20 at 14:05
  • if ```r``` is ```(escaper (lambda (continuation) (continuation body)))```, result of ```(r continuation)``` is still ```(continuation body)``` since ```continuation``` is also an escape procedure and invoked first. it is no difference that r is ```(escaper (lambda (continuation) (continuation body)))``` or ```(lambda (continuation) (continuation body))```. (sorry for my bad english) – Lucas Apr 27 '20 at 14:28
  • you repeat the conclusion of my answer. :) I was a bit more careful at arriving at it. I give translation and work through it carefully. But if it is so clear for you, why have you asked? :) but it's good that you asked, it gave me a chance to work through this exercise. :) cheers! – Will Ness Apr 27 '20 at 14:37
  • i can solve the question preceding the one i asked. but feel confused in this one. after reading the first line of your answer, i rethought this question, understood why it is always. – Lucas Apr 27 '20 at 15:00
  • so my answer was useful? ;) – Will Ness Apr 27 '20 at 15:07
  • @WillNess yeah, of course! u inspired me! – Lucas Apr 27 '20 at 17:14
  • 1
    glad to be of help. :) (notice the re-writes with `let`. it often helps me to understand code when I do such re-writes, like [with y-combinator](https://stackoverflow.com/a/11864862/849891)) – Will Ness Apr 27 '20 at 17:17
  • @WillNess thanks for reminding :) i will try to take in the skills u used. – Lucas Apr 27 '20 at 23:31

1 Answers1

2

The answer is: always.

escaper is not part of Scheme. It is defined by that book, Scheme and the Art of Programming, thus:

" escaper turns its argument procedure into similarly defined 'escape' procedure (a.k.a. 'continuation'), which, when invoked, its result becomes the result of the entire computation. Anything awaiting the result [of that escape procedure's invocation] is ignored." (slightly copy-edited)

The result of (continuation body) in the " escaper-ed" version of (lambda (c..n) (c..n body)) would be returned directly into the top level, except, continuation does not return. It jumps into its destination context (1), i.e. that which awaits the result of the (call/cc r) call, because this continuation is set up by that call to call/cc:

           ;; (0)   -- top level
             (... 
                  ;; (1)  <-----------------------------------\
                    (call/cc r)  ;; r = (escaper (lambda (continuation)
                                 ;;                 (continuation body)))
                         ...)
===
           ;; (0)   -- top level
             (... 
                  ;; (1)  
                    (continuation--0                       ;; set up by `escaper`
                      ((lambda (continuation)
                            (continuation body))
                        continuation--1))                   ;; set up by call/cc
                         ...)
===
           ;; (0)   -- top level
             (... 
                  ;; (1)  
                    (continuation--0
                       (let ((continuation continuation--1))   ;; by application of `lambda`
                         (continuation body)))
                         ...)

So if body returns, that result is passed into (1) by continuation--1; and if body calls continuation with a value, that value is passed into (1) by continuation--1. Nothing is returned to continuation--0, so its jump is never triggered.

And in

           ;; (0)
             (... 
                  ;; (1)
                    (call/cc (lambda (continuation) body))
                         ...)
===
           ;; (0)
             (... 
                  ;; (1)
                    (let ((continuation continuation--1)) 
                       body)
                         ...)

exactly the same thing happens: if body returns, that result is simply returned into (1); and if body calls continuation with a value, that value is passed into (1) by continuation--1.

Will Ness
  • 62,652
  • 8
  • 86
  • 167