本来 Smalltalk ではこんなふうには絶対書かないので、あまり忠実にしても意味はないかなぁと最初思ったのですが、実際に書いてみたらなかなかおもしろかったので。
次のが Ruby がやっていることを再現したコード。ワークスペース変数を使っているので、ワークスペースにコピペして選択後、do it (alt/cmd + d) すると実行できます(Squeak4.2-ja-all-in-one で動作確認)。
"ネームスペースにキー値を登録するとグローバル変数になる" "配列は固定長なので代わりに an OrderedCollection を使う" Smalltalk at: #db put: OrderedCollection new. "an Object の main とそのナンチャッテ特異クラスを作成" main := Object new assureUniClass. "Smalltalk にはメソッド定義構文式がないのでメッセージングで" main class compile: 'addRecordTitle: title artist: artist rating: rating ripped: ripped "ハッシュ(Smalltalk では辞書)のリテラルは無いので変換して生成" db add: ({#title->title. #artist->artist. #rating->rating. #ripped->ripped} as: Dictionary)'. main class compile: 'dumpDb db do: [:cd | cd keysAndValuesDo: [:key :val | Transcript cr; show: (key asUppercase forceTo: 10 paddingWith: $ ); show: val]. Transcript cr; endEntry]'. "#fileNamed:do: は Ruby からのパクリ" main class compile: 'saveDb: filename FileStream forceNewFileNamed: filename do: [:file | file nextPutAll: db storeString]'. main class compile: 'loadDb: filename db := Compiler evaluate: ( FileStream fileNamed: filename do: [:file | file contents])'. "デモ用にデータベースクリア用のメソッドを追加" main class compile: 'clearDb db removeAll'.
実行例
main addRecordTitle: 't1' artist: 'a1' rating: 4 ripped: true. main addRecordTitle: 't2' artist: 'a2' rating: 3 ripped: false. main addRecordTitle: 't3' artist: 'a3' rating: 2 ripped: true. "標準出力もどきを起動" Transcript open. main dumpDb. main saveDb: 'db.txt'. main clearDb. main loadDb: 'db.txt'. main dumpDb.
出力
TITLE t1 ARTIST a1 RATING 4 RIPPED true TITLE t2 ARTIST a2 RATING 3 RIPPED false TITLE t3 ARTIST a3 RATING 2 RIPPED true TITLE t1 ARTIST a1 RATING 4 RIPPED true TITLE t2 ARTIST a2 RATING 3 RIPPED false TITLE t3 ARTIST a3 RATING 2 RIPPED true