これは「Ruby脳にはCrystalつらい Advent Calendar 2015」の22日目の記事です。
タイトルのまんまですが、Crystal は Thread がなくてつらい。
Thread というクラスはありますが、ソースを見ると、
# Don't use this class, it is used internally by the event scheduler. # Use spawn and channels instead.
と書いてあって気軽に使える雰囲気ではありません。
spawn や channel を使えと書かれてるので spawn を使ってみます。
spawn do 10.times do |i| print 'a' sleep 1 end end spawn do 10.times do |i| print 'b' sleep 1 end end gets
このプログラムを動かすと次のようになります。
% crystal hoge.cr bababababaababababab
a と b が交互に出力されて、ちゃんと並列動作しているようです。
なお、sleep がないと交互にはなりません。spawn は Fiber で実装されていて、sleep によってコンテキストを切り替えているようです。 つまりスレッドと違い、複数 CPU を同時に使うことはできません。
上の例では最後に gets でキー入力を待っていますが、Channel を使えば待ち合わせができるようです。
chann = Channel(Bool).new spawn do 10.times do print 'a' sleep 1 end chann.send true end spawn do 10.times do print 'b' sleep 1 end chann.send true end chann.receive chann.receive
Channel は Crystal のドキュメントに説明がなくてよくわからないのですが、Ruby の Queue みたいなもんでしょうか。
Channel を各 spawn ブロックの中で使えば sleep を使わなくてもコンテキスト切り替えができるようです。