AWS EC2上で並列処理の時間を再々計測した - @ledsun blog で、次の3つの仮説を立てました。
また1は可能性が低いと判断しました。 今回は3の可能性を検証します。
対象の処理は全体はActiveJobで実装しています。 そこで次のようなコールバックを定義して、GCの実行回数をしらべます。
around_perform do |job, block| GC.start GC.stat => {minor_gc_count: prev_minor_gc_count, major_gc_count: prev_major_gc_count} block.call ensure GC.stat => {minor_gc_count: minor_gc_count, major_gc_count: major_gc_count} tengu_p minor_gc_count - prev_minor_gc_count, major_gc_count - prev_major_gc_count end
右代入というやつを初めて使いました。 余談です。
計測した結果は次の通りです。 249文章を処理しおわった時にジョブを中止して、その間に発生したGCの数を数えました。
minor_gc_count | major_gc_count | |
---|---|---|
Ractorなし | 264 | 12 |
コピー2回 | 227 | 14 |
コピー1回 | 308 | 17 |
コピー回数とGCの回数には相関がありません。 「コピーで作られたオブジェクトのGCがボトルネックだった」の可能性も低そうです。
消去法で「コピーは減ったが相変わらずボトルネックである」の可能性が高くなりました。 ここに注力するのが良さそうです。