Search code examples
schemecontinuationscoroutine

Seeking contrived example code: continuations!


So I believe I understand continuations now, at least on some level, thanks to the community scheme wiki and Learn Scheme in Fixnum Days.

But I'd like more practice -- that is, more example code I can work through in my head (preferably contrived, so there's not extraneous stuff to distract from the concept).

Specifically, I'd like to work through more problems with continuations that resume and/or coroutines, as opposed to just using them to exit a loop or whatever (which is fairly straightforward).

Anyway, if you know of good tutorials besides the ones I linked above, or if you'd care to post something you've written that would be a good exercise, I'd be very appreciative!


Solution

  • Yeah, continuations can be pretty mind-bending. Here's a good puzzle I found a while back - try to figure out what's printed and why:

    (define (mondo-bizarro)
      (let ((k (call/cc (lambda (c) c)))) ; A
        (write 1)
        (call/cc (lambda (c) (k c))) ; B 
        (write 2)
        (call/cc (lambda (c) (k c))) ; C
        (write 3)))
    
    (mondo-bizarro)
    

    Explanation of how this works (contains spoilers!):

    1. The first call/cc stores returns it's own continuation and stores it in k.
    2. The number 1 is written to the screen.
    3. The current continuation, which is to continue at point B, is returned to k, which returns to A
    4. This time, k is now bound to the continuation we got at B
    5. The number 1 is written again to the screen
    6. The current continuation, which is to continue at point B, is returned to k, which is another (but different) continuation to another point B
    7. Once we're back in the original continuation, it's important to note that here k is still bound to A
    8. The number 2 is written to the screen
    9. The current continuation, which is to continue at point C, is returned to k, which returns to A
    10. This time, k is now bound to the continuation we got at C
    11. The number 1 is written again to the screen
    12. The current continuation, which is to continue at point B, is returned to k, which returns to C
    13. The number 3 is written to the screen
    14. And you're done

    Therefore, the correct output is 11213. The most common sticking point I've put in bold text - it's important to note that when you use continuations to 'reset' the value of k that it doesn't affect the value of k back in the original continuation. Once you know that it becomes easier to understand.