选择很多很多......有点儿

时间:2009-07-01 09:33:05

标签: ruby-on-rails find associations

这是我在Stack上的第一篇文章,如果我违反任何协议,请耐心等待。

我正在研究Rails(2.1.2)中的一个项目,我有一个如下所示的关系场景:

event [has_many] days

人(在不同类别中)可以注册活动日,并提供以下绑定结果:

category [has_many] customers [has_many] orders [has_many] days  
[belongs_to] event

现在,我想为一个客户或特定类别的所有客户提供“事件”的总数,而且我被卡住了。 AFAIK,没有办法通过一系列对象执行简单的“查找”,对吗?那么,解决方案是什么呢?嵌套循环,以及从订单中的'天'获取'事件'的收集方法?

如果我不清楚,请告诉我。

感谢您的帮助!

2 个答案:

答案 0 :(得分:0)

您的模型可能如下所示:

class Category
  has_many :customers

class Customer
  has_many :orders
  has_many :days, :through => :orders # I added this
  belongs_to :category

class Order
  has_many :days
  belongs_to :customer

class Day
  belongs_to :event
  belongs_to :order

class Event
  has_many :days

有了这个,您可以为客户计算事件:

events = customer.days.count(:group => 'event_id')

它会像这样返回OrderedHash:

#<OrderedHash {1=>5, 2=>13, 3=>0}>

您可以通过以下方式获取事件:

events[event_id]

events[1] # => 5
events[2] # => 13
etc.

如果您想要uniq事件的总数:

events.size # => 3

如果计算类别中所有客户的事件,我会做这样的事情:

events = {}
category.customers.each {|c| events.merge!(c.days.count(:group => 'event_id') ) }
events.size # => 9 - it should be total number of events

但在这种情况下,您会丢失每个事件出现次数的信息。

我没有对此进行测试,因此可能会出现一些错误。

答案 1 :(得分:0)

我个人会使用MySQL语句来做这件事。我不确定,但我认为它比其他示例(使用rails提供的关联方法)快得多。

这意味着在Customer模型中,您可以执行以下操作: (请注意,我假设您使用的是默认关联键:'model_name_id')

class Customer
  def events
    Event.find_by_sql("SELECT DISTINCT e.* FROM events e, days d, orders o, customers c WHERE c.id=o.customer_id AND o.id=d.order_id AND e.id=d.event_id")
  end
end

这将返回与用户关联的所有事件,并且不会重复('DISTINCT'关键字确保这一点)。与上面的示例一样,您将丢失有关用户注册日期的信息。如果您需要这些信息,请说明。

另外,我没有为你的分类模型添加一个例子,因为我认为你可以自己调整我的例子。如果没有,请告诉我。

修改

我刚看你就是想要计算一下这些事件。使用count语句可以更快地(或至少,更少的内存密集型)完成。要使用它,只需使用以下功能:

def event_count
  Event.count_by_sql(SELECT DISTINCT COUNT(e.*) FROM ... ... ...
end