Smalltalk-72で学ぶOOPの原点:知らないメッセージはスルーする?

アラン・ケイの“オブジェクト指向”というアイデアをもとに(非同期処理などいろいろ足りていないながらも──)比較的忠実に実装された1970年代の非常に古いSmalltalk-72で遊んでみるシリーズです(なお最新のSmalltalkについては Pharo などでお楽しみください!)。他の記事はこちらから→Smalltalk-72で学ぶOOPの原点 Advent Calendar 2019 - Qiita


継承が…ない!(「is?」の実装))からの続き)

知らないメッセージは基本スルーするSmalltalk-72

isパターン未定義時のis?の挙動の不思議はひとまず置いておくとして、Smalltalk-72でオブジェクトが知らない(パターン未定義の)メッセージを受け取ったときの挙動を確かめておきましょう。

ためしに3hogeを送ってみます。

f:id:sumim:20191211175711p:plain
「3」に「hoge」を送ってみる

すると、エラーになります。

f:id:sumim:20191211175827p:plain
エラーが出るが…

ただ「シンボル(hogeを指す)は値を持たない」というちょっと不思議なエラーになります。

ちなみに参考まで、今のSmalltalkでは「そんなメッセージ、知らない」がこういうときのエラーの基本です。

f:id:sumim:20191211180341p:plain
Pharo Smalltalkで「3」に「hoge」を送ったときのエラー

実は、Smalltalk-72では知らないメッセージは基本スルーする仕組みになっており、したがって、続くメッセージを新しい式の始まりと認識されます。つまり、続くメッセージの最初のトークンは次のメッセージ式のレシーバーになるので、hogeは変数として認識され、それに値が代入されていないという件のエラーになるわけです。

試しに、あらかじめhoge4を代入しておいてから改めて3 hoge を評価してみましょう。

f:id:sumim:20191211180735p:plain
あらかじめ「hoge」に「4」を代入して「3 hoge」を実行すると…

なるほど4が返ります(このとき3はREPLで複数の式を評価したときの一つ前の式と同じ扱いとなり、普通に破棄され結果=出力には影響を与えません)。

知らないメッセージは基本スルーというのは、悪名高きObjective-Cnilの挙動(もっとも彼はオブジェクトですらないので、知っているメッセージなど無く、すべてのメッセージをスルーするわけですが…)を彷彿とさせて、なんだかちょっと残念ですね。これについては、アラン・ケイのアイデアに忠実にした結果なのか、はたまたただ単純に実装の都合や運用の妙の類いに過ぎないのか、もう少し調べてみたいと思います。

isアクション

ということで、実はALLDEFS(ブートストラップコード)にはto is …で始まるisアクションが別に定義されていて、isメッセージに対応できないオブジェクトにis?等のメッセージが送信されたとしても、レシーバーがそれに応答する代わりにisアクションがコールされ(それに改めて?が送られることで)untypedを返すことができる、というのがこのカラクリの答でした。

f:id:sumim:20191211181311p:plain
「is」アクションの定義

念願のクリック、's(instance_evalで使う記号)、⦂(オープンコロン)を手に入れた!に続く)