Blog

perl6 ではコールバックを受け取る関数では Sub を受け取るように明示する

perl6 では以下のようなコードでは 3 が帰る。

(sub { (-> { return 3 })(); return 4 })().say

-> { } という記法からすると sub { } と同義なように見えるが実はそうではない。これは perl5 の BLOCK と同じことだ。 つまり以下と同じ。

perl -E 'say sub { map { return 1 } 2; return 3 }->()'

なので、この中で return すると上に抜けてしまう。

> (-> { }).WHAT.say
(Block)
> (sub { }).WHAT.say
(Sub)

実際のところ、そもそも Block と Sub で型も違うので、一般にコールバック関数を受け取るようなメソッドを定義する際には以下のように Sub を受け取るように明示すべき。

method run(Sub $app) { ... }

明示しておかないと、処理がなぜか突然上のほうにすっぽぬけたりしてマジで意味不明になるので辛いです.