これは私が本当に理解できない奇妙なことです。私はPostGreSql9.2で作業しています...
私はこのデータベースを持っています:
movies (id, title, votes)
infos (id, movie_id, info_type, value)
movie.votes を infos.value で更新し、movies.id = infos.movie_if に参加し、info_type = 100 (これは投票のタイプです..)
私は2つの異なるクエリを試しました:
update movies
set votes = cast(i.value as integer)
from movies m inner join infos i on m.id = i.movie_id
where i.info_type = 100
これは (explain を使用して) 約 1100 万秒の実行時間を予測します (多すぎます!)
2回目の試行:
update movies m
set votes = cast(
(
select value
from infos i
where i.info_type = 100 and i.movie_id = m.id
limit 1
) AS integer);
これは「わずか」2万秒であるはずです..それでも多すぎます
クエリプランがどのように機能するのかよくわからないので、(active_record を使用して) ruby スクリプトでこれを実行しようとしています...これは次のとおりです。
Info.find_in_batches(:conditions => "info_type = 100") do |group|
group.each{ |info|
movie = Movie.find(info.movie_id)
movie.votes = info.value.to_i
movie.save
}
end
ruby を読んでいない人のために説明すると、このクエリは、info_type = 100 の条件を満たすすべての情報を単純にループし、それぞれの情報について、対応するムービーを検索して更新します。
そして、それは非常に速かったです!ほんの数分で、すべてのルビー/オームのオーバーヘッドが発生します!!
さて、なぜ?? 映画には約 600k のレコードがあることを知っていますが、200k (3 分の 1) だけが投票数の情報レコードを持っています。それでも、これは何が起こっているのかを説明していません。