この記事はアピリッツの技術ブログ「DoRuby」から移行した記事です。情報が古い可能性がありますのでご注意ください。
大量のレコードに対してデータ処理を行う場合, ActiveRecordのpluckを使用することが有効な場合が存在する. 本記事では、処理速度向上に関する有効性の確認を行う.
処理内容
テーブル内の全レコードに対して、
現在レコードが所持しているパラメータを利用して、更新をかける処理
- レコード:50万件
- パラメータ:25種類
動作比較
1. レコード1件ごとに更新をかける(比較用)
比較用に1件ごとに更新をかける処理を行ってみたところ、
処理に時間がかかり実行が終わらないため、問題外であった
2. find_each
- find_eachでレコードを取得して、パラメータごとのリストを作成
- リストのパラメータごとに、update_allで更新をかける
処理の所要時間およそ10分
1SQL自体のログに出力されるSQL実行時間,
発行されるSQLの構文への explain の実行でのインデックスの適用具合自体は問題が無いように見られたが,
ActiveRecordオブジェクト生成にかかるコストが処理速度に影響を与えている可能性が考えられる.
3. pluck
- pluckで、パラメータごとのリスト作成に必要なカラムの値を取得
- リストのパラメータごとに、update_allで更新をかける
処理の所要時間およそ30秒
ActiveRecordオブジェクト生成を防ぐことにより,
同一のリスト作成処理において大幅な処理速度向上が見込まれた.
まとめ
上記のことから,
pluckの返却値はArrayでの取得となるため, ActiveRecordのメソッド等は使用できなくなるが,
取得値のみで処理が可能な場合など利用可能な場面においては,
pluckを使用することにより, 処理速度向上を行うことができることを確認することができた.