2014-11-14 28 views
0

我需要做一堆查询。如何在Rails上减少这种情况下的查询数量

在这种情况下,我觉得我的很多次查询的结果,

在一个查询未完成。

如何使我的搜索结果可以通过一个查询完成?

q = WeatherLog.nearby(100, longitude, latitude) 
    if start_time and end_time 
    @weather_logs = q.where(datetime: start_time..end_time) 
    elsif start_time 
    @weather_logs = q.where("datetime > ?", start_time) 
    elsif end_time 
    @weather_logs = q.where("datetime < ?", end_time) 
    end 
    @weather_logs = @weather_logs.order(datetime: :asc).first(2000) 

回答

1

首先要认识到的是,ActiveRecord不会执行一个查询,直到它完全必须(懒加载)。虽然有许多代码构建查询,但查询只能在.all,.each,.first等方法上执行。因此,从性能的角度来看,您的代码是可以的,因为您只能执行一个对数据库的查询,而不是很多。

但是你可以调整代码,使其更加人性化的可读性和可维护性:

class WeatherLog < ActiveRecord::Base 
    # ... 
    class << self 
    def between_times(times) 
     after_time(times[:start_time]).before_time(times[:end_time]) 
    end 

    def after_time(time) 
     return self.all if time.nil? 
     where('datetime > ?', time) 
    end 

    def before_time(time) 
     return self.all if time.nil? 
     where('datetime < ?', time) 
    end 
    end 
end 

使用self.all有效地跳过查询条件,同时仍然能够查询链接。这使得可以移除所有的if/else逻辑。然后您可以链接查询(或在WeatherLog内创建帮助方法):

WeatherLog.nearby(100, longitude, latitude).between_times(start_time: start_time, end_time: end_time)