【问题标题】:Scope Order by Count with Conditions Rails使用条件 Rails 按计数范围排序
【发布时间】:2019-07-03 19:28:50
【问题描述】:

我有一个模型 Category 那个 has_many Pendencies。我想创建一个范围,按具有active = true 的待定数量对类别进行排序,但不排除active = false

到目前为止我所拥有的是:

scope :order_by_pendencies, -> { left_joins(:pendencies).group(:id).order('COUNT(pendencies.id) DESC')}

这将按挂件数量排序,但我想按具有active = true 的挂件进行排序。

另一个尝试是:

scope :order_by_pendencies, -> { left_joins(:pendencies).group(:id).where('pendencies.active = ?', true).order('COUNT(pendencies.id) DESC')}

这将按具有pendencies.active = true 的挂起数排序,但不包括pendencies.active = false

感谢您的帮助。

【问题讨论】:

  • 嘿伙计。订单标签上写着不要使用。我不太明白你的问题,但标签必须删除。
  • 你好,约书亚。谢谢你的回答。我真的不明白你所说的订单标签是什么意思。我的问题是这样的:假设我有以下内容:类别 1 有 10 个挂件(2 个活动 = true 和 8 个活动 = false);类别 2,有 8 个未决项(6 个活动 = 真,2 个活动 = 假);类别 3 有 15 个未决项(15 活动 = 假)我希望订单为:类别 2、类别 1、类别 3
  • 我可以用 C# 解决这个问题。抱歉,我不认识 Ruby。
  • 感谢您的尝试,Jushua。您能否在 C# 中发布您的答案?如果我看到它,也许我可以有一个洞察力

标签: ruby-on-rails sorting count scope conditional-statements


【解决方案1】:

我猜你想按活动挂起的数量排序,而不忽略没有活动挂起的类别。

应该是这样的:

scope :order_by_pendencies, -> { 
  active_count_q = Pendency.
    group(:category_id).
    where(active: true).
    select(:category_id, "COUNT(*) AS count")

  joins("LEFT JOIN (#{active_count_q.to_sql}) AS ac ON ac.category_id = id").
    order("ac.count DESC")
}

等效的 SQL 查询:

SELECT *, ac.count 
FROM categories
LEFT JOIN (
    SELECT category_id, COUNT(*) AS count
    FROM pendencies
    GROUP BY category_id
    WHERE active = true
  ) AS ac ON ac.category_id = id
ORDER BY ac.count DESC

请注意,如果某个类别没有活动的未决项,则计数将为空,并将添加到列表的末尾。 可以添加一个类似的子查询以额外按未决总数排序...

【讨论】:

    【解决方案2】:

    按要求回答 C#:

    method() {
        ....OrderBy((category) => category.Count(pendencies.Where((pendency) => pendency.Active))
    }
    

    或者直接使用 SQL:

    SELECT category.id, ..., ActivePendnecies
      FROM (SELECT category.id, ..., count(pendency) ActivePendnecies
              FROM category
              LEFT JOIN pendency ON category.id = pendency.id AND pendnecy.Active = 1
              GROUP BY category.id, ...) P
     ORDER BY ActivePendnecies;
    

    我们必须在 SQL 中输出 ActivePendnecies,即使代码会将其丢弃,否则优化器有权丢弃 ORDER BY

    【讨论】:

      【解决方案3】:

      目前我开发了以下方法(它正在工作,但我认为这不是最好的方法):

        scope :order_by_pendencies, -> { scoped = Category.left_joins(:pendencies)
                                                  .group(:id)
                                                  .order('COUNT(pendencies.id) DESC')
                                                  .where('pendencies.active = ?', true)
                                         all = Category.all
                                         (scoped + all).uniq}
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2017-06-16
        • 2017-06-25
        • 1970-01-01
        • 1970-01-01
        • 2014-01-30
        • 1970-01-01
        • 2011-06-25
        • 2015-04-29
        相关资源
        最近更新 更多