[Rails] Getting random db entries...

Jeremy Kemper jeremy at bitsweat.net
Wed Mar 16 21:29:57 GMT 2005


Josef Pospisil wrote:
> I'm doing it like this:
> 
>>questions = self.find_by_sql(
>     ["select id from questions where area_id = ? and score = ?",
>     area_id, score])
>>questions.sort! {rand(3) - 1}[1..count].collect do |q|
>     Question.find(q.id)
>>end
> 
> So if you need only ids that collect thing is not necessary. If anyone
> have any comments on this code please mail me cause it's one of the
> bottleneck for my app, and maybe I'm doing something wrong.

You can cut down the number of queries from N+1 to 2:

module Enumerable
  def random_sample(n)
    sort_by { rand }.slice(0, n)
  end
end

class Question < ActiveRecord::Base
  SELECT_IDS_BY_AREA_AND_SCORE = "select #{primary_key} from
#{table_name} where area_id=? and score=?".freeze

  def self.random_sample(area_id, score, n = 3)
    area_id = area_id.id if area_id.is_a?(Area)
    find(find_by_sql([SELECT_IDS_BY_AREA_AND_SCORE, area_id,
score]).random_sample(n).map { |q| q.id })
  end
end

Calling find with an array of ids will generate 1 "select * from
questions where id in (?)" intead of N "select * from questions where id
= ?".

jeremy


More information about the Rails mailing list