标题有点令人困惑。但是我有一个表来保存来自不同类别的用户的条目。因此,有类别A
,B
和C
,用户可能在每个类别中都有多个条目。我需要一个SQL查询,它将获得每个类别的最新1条目(按created_at
排序),希望在一个查询中。这是Rails,因此它可以是实际的SQL查询或ActiveRecord。
使用的列将是user_id
,category
(只有A
,B
或C
),created_at
和notes
(这是我需要的实际信息)。
答案 0 :(得分:0)
试试这个(假设你i
表中提到的所有列都存在):
to
答案 1 :(得分:0)
我们假设这里有一位用户(您的标题是for a specific user
)。
基本上我们是在询问:
SELECT "entries".* FROM "entries"
LEFT JOIN entries e2 ON (
entries.category=e2.category AND
entries.created_at < e2.created_at AND
entries.user_id = e2.user_id)
WHERE e2.id IS NULL AND entries.user_id=?
翻译成Rails:
user_id = @user.id
data = Entry.joins(%q{LEFT JOIN entries e2 ON (
entries.category = e2.category AND
entries.created_at < e2.created_at AND
entries.user_id = e2.user_id
)}).where("e2.id IS NULL AND entries.user_id = ?", user_id)
如果您需要按类别分类的最后一个音符,请从res
by_category = data.map{|e| [e.category, e.notes]}.to_h
注意您的要求是按created_at
日期比较条目。我建议改用id
。所以你可以这样写:
user_id = @user.id
data = Entry.joins(%q{LEFT JOIN entries e2 ON (
entries.category = e2.category AND
entries.id < e2.id AND
entries.user_id = e2.user_id
)}).where("e2.id IS NULL AND entries.user_id = ?", user_id)
答案 2 :(得分:0)
以下是三种简单的SQL方法,还有更多,但我不确定MySQL支持窗口函数的程度等等。
1查找created_at是该user_id和类别的最大值的条目。如果两个条目具有相同的created_at作为两行,则将返回一个用户和类别的问题。
select *
from entries
where created_at = (
select max(e.created_at)
from entries e
where e.user_id = entries.user_id and
e.category = entries.category)
2通过created_at desc查找按行排序时该用户的第一个ID和类别的条目。如果两个条目与返回的一行具有相同的created_at是有问题的,那么您也可以通过id进行排序以实现此目的。
select *
from entries
where id = (
select e.id
from entries e
where e.user_id = entries.user_id and
e.category = entries.category
order by created_at desc
limit 1)
3查找没有其他人为该用户和类别设置更大的created_at的条目。如果两个条目具有相同的created_at作为两行,则将返回一个用户和类别的问题。
select *
from entries
where not exists (
select e.id
from entries e
where e.user_id = entries.user_id and
e.category = entries.category and
e.created_at > entries.created_at)
所有这些应该非常有效,但没有一个非常适合在ActiveRecord中表达。它们中的任何一个都可以将where子句表示为作用域,只是将它很好地封装在模型中,然后它就可以合并到一个关联中:
has_many :latest_category_entries, -> {merge(:latest_category)}, class_name => "Entry"
...所以你可以:
@user.latest_category_entries
和
User.includes(:latest_category_entries).each do |user|
user.latest_category_entries.each do |entry|
etc ...