call/cc使ってみる3

call/cc 入門 (Coroutine with call/cc) - MAYAHの前半を読んでみた。
演習問題みたいなのがあったので、やってみた。

gosh> (define cont #f)
cont
gosh> (and (call/cc (lambda (c) (begin (set! cont c) 10)))
           (begin (display 'a) 10))
a10
gosh> (cont 10)
a10

(cont 10)の実行で、何が起きてんのかな?
「call/cc の値を x にしてλ抽象」らしいので、contは

(lambda (x)
  (and x (begin (display 'a) 10)))

になるかなぁ、と。んで、

実は、continuation は「continuation が呼ばれると、continuation が作られた call/cc の外に、引数を call/cc の返り値としてジャンプする」というのが正しい振る舞いです。

call/cc 入門 (Coroutine with call/cc) - MAYAH

ということらしいけど、これに従うならば、

contが呼ばれると、(call/cc (lambda (c) (begin (set! cont c) 10)))の外に、10をcall/ccの返り値としてジャンプする

という具合になる。 つまり、

(and 10 (begin (display 'a) 10))

ってことになるのかな?
やってみよう。

gosh> (and 10 (begin (display 'a) 10))
a10

うん、同じ結果になった。
同じ要領で、残りの演習もやってみる。

gosh> (define cont #f)
cont
gosh> (and (begin (display 'a) 10)
           (call/cc (lambda (c) (begin (set! cont c) 10))))
a10
gosh> (cont 10)
10
gosh> (begin (cont 10) (display 'c))
10

この場合、contは

(lambda (x)
  (and (begin (display 'a) 10)
       x))

だから、(cont 10)は

(and (begin (display 'a) 10)
     10)

になるのかな?実行してみる。

gosh> (and (begin (display 'a) 10)
           10)
a10

あれ?結果が違う。
もいっちょ。(begin (cont 10) (display 'c))は

gosh> (begin (and (begin (display 'a) 10)
                  10)
             (display 'c))
ac#<undef>

ん〜?これも違う。


最後。

gosh> (define cont #f)
cont
gosh> (begin (display 'a)
             (call/cc (lambda (c) (set! cont c) (display 'b)))
             (display 'c))
abc#<undef>
gosh> (cont #f)
c#<undef>

contは

(lambda (x)
  (begin (display 'a)
         x
         (display 'c)))

で、実行してみると

gosh> (begin (display 'a)
             #f
             (display 'c))
ac#<undef>

んんんんんん〜?また違う。


もう一回引用するけど、

実は、continuation は「continuation が呼ばれると、continuation が作られた call/cc の外に、引数を call/cc の返り値としてジャンプする」というのが正しい振る舞いです。

これがミソなんだと思うけど、よく理解できない。