Postgresql 如何获取每个组中所有列+每个组一个组计数列的最新记录?
考虑下表:Postgresql 如何获取每个组中所有列+每个组一个组计数列的最新记录?,postgresql,Postgresql,考虑下表: CREATE TABLE event( event_id UUID PRIMARY KEY, user_id UUID NOT NULL, trigger_id UUID NOT NULL, name VARCHAR (255) NOT NULL, type VARCHAR (50) NOT NULL, trigger_name VARCHAR (255) NOT NULL, status smallint, date_
CREATE TABLE event(
event_id UUID PRIMARY KEY,
user_id UUID NOT NULL,
trigger_id UUID NOT NULL,
name VARCHAR (255) NOT NULL,
type VARCHAR (50) NOT NULL,
trigger_name VARCHAR (255) NOT NULL,
status smallint,
date_created TIMESTAMP NOT NULL DEFAULT NOW(),
);
我想
首先按类型ASC订购,然后按创建日期说明订购
这部分很容易做到
SELECT *
FROM event
WHERE user_id = 'fd80059a-3a16-40fe-9f6b-ad2812875d92'
ORDER BY type ASC, date_created DESC
2按触发器id、类型和名称分组,每组计数。是的,如果触发器id、类型和名称相同,我想创建一个组,并显示最近的一个组,其中包含组中所有事件的计数,即事件发生的次数,因为如果这3个相同,则可以认为事件相关
这是最具挑战性的部分。理想情况下,类似这样的方法会起作用:
SELECT * --, count(since the count/grouping is based on 3 columns, how??)
FROM event
WHERE account_id = 'fd80059a-3a16-40fe-9f6b-ad2812875d92'
ORDER BY type ASC, date_created DESC
GROUP BY trigger_id, type, name
将只给我每个组中的第一条记录,因为它们已按日期排序,但包含所有列,而不仅仅是GROUPBY子句中的列+最后的group count列
我现在使用选项1解决这个问题,然后在我的节点API中使用以下javascript代码,但是如果您理解这个代码片段,它正是我在postgres中需要做的事情:
[...arrayOfEventsFromDB.reduce((r, o) => {
const key = `${o.trigger_id}-${o.type}-${o.name}`;
const item = r.get(key) || Object.assign({}, o, {
count: 0,
});
item.count++;
return r.set(key, item);
}, new Map).values()];
但在理想情况下,如果postgres非常适合这种聚合,我希望在SQL查询中使用它
编辑
因为我无法将注释中的代码粘贴到答案
根据要求,这里是一个正在运行的小提琴与表的创建,数据和选择查询我已经提出了,通过结合以下两个答案。使用所有这些子选项似乎有点低效,但有效
要拯救您,请编辑:并在以下位置进行区分:
编辑:聊天后此解决方案最适合:
SELECT *
FROM (
SELECT DISTINCT ON (trigger_id, type, name)
*
FROM (
SELECT *
FROM (
SELECT
*,
COUNT(*) OVER (PARTITION BY trigger_id, type, name)
FROM event
WHERE user_id = 1
) s
) t
ORDER BY trigger_id, type, name, date_created DESC
) u
ORDER BY type ASC, date_created DESC
你可以在下面查询
SELECT *
FROM (
SELECT
a.*,
COUNT(*) OVER (PARTITION BY trigger_id, type, name) cnt , row_number () over(PARTITION BY trigger_id, type, name order by date_created DESC ) rn
FROM event a
WHERE account_id = 'fd80059a-3a16-40fe-9f6b-ad2812875d92'
) s
where rn < = 4
ORDER BY type ASC, date_created DESC
谢谢虽然我得到了正确的计数,但我仍然得到了所有记录。不要分组。最后我只想展示4张唱片。基于为每个组创建的日期的最新版本。@Dac0d3r已更新。对于更精确的代码,我真的需要样本代码和预期的输出,请编辑您的问题非常感谢。请看我在文章底部的编辑。我不得不调整一下,但它似乎起作用了。只是速度很慢,即使我的表中只有14条记录。现在请向我们展示您的数据。14记录不应该有这样的影响。也许我的表现不好,表现还不错。我想我有一些网络延迟影响了它。我不得不走了,但我回来后会更新。我会试着做一把小提琴。谢谢!!谢谢没用,但你的行号技巧似乎是每个小组只选择第一条记录的关键。根据你和S-man的回答,我可以在这里用一个有效的SQL组合成一把小提琴,但是对于所有这些嵌套的子选择,它似乎不是最好的实现@Dac0d3r很高兴知道它有帮助。如果您有更好的解决方案,您可以发布并接受相同的解决方案。最后的动机是互相帮助,互相学习。
SELECT *
FROM (
SELECT DISTINCT ON (trigger_id, type, name)
*
FROM (
SELECT *
FROM (
SELECT
*,
COUNT(*) OVER (PARTITION BY trigger_id, type, name)
FROM event
WHERE user_id = 1
) s
) t
ORDER BY trigger_id, type, name, date_created DESC
) u
ORDER BY type ASC, date_created DESC
SELECT *
FROM (
SELECT
a.*,
COUNT(*) OVER (PARTITION BY trigger_id, type, name) cnt , row_number () over(PARTITION BY trigger_id, type, name order by date_created DESC ) rn
FROM event a
WHERE account_id = 'fd80059a-3a16-40fe-9f6b-ad2812875d92'
) s
where rn < = 4
ORDER BY type ASC, date_created DESC