我有一个带有date
和room
列的大型邮件表。和20亿行。
现在我只希望每个房间保留最后50条消息并删除以前的消息。
我可以使用快速查询吗?
此问题是唯一的,我没有找到关于分组和有序选择中的删除行的任何其他问题
您无法在快速查询中执行此操作。您有很多数据。
我建议创建一个新表。然后,如有必要,您可以替换第一个表中的数据。
可能是获得50行的最有效方法-假设date
对于每个room
是唯一的]]
select t.* from t where t.date >= coalesce((select t2.date from t t2 where t2.room = t.room order by t2.date desc limit 1 ), t.date );
为了对此有性能的希望,您需要在
(room, date)
上建立索引。
您也可以在MySQL 8+中尝试row_number()
:
select . . . -- list the columns from (select t.*, row_number() over (partition by room order by date desc) as seqnum from t ) t where seqnum <= 50;
然后您可以通过执行以下操作替换数据:
create table temp_t as select . . . -- one of the select queries here; truncate table t; -- this gets rid of all the data, so be careful insert into t select * from temp_t;
大规模插入比大规模更新效率更高,因为不需要记录旧数据(也不锁定页面和其他内容)。
DELETE T FROM YOURTABLE T
LEFT JOIN (
SELECT *,
RANK() OVER (PARTITION BY
ROOM
ORDER BY
[DATE] DESC
) DATE_RANK
) AS T2
ON T.[DATE] = T2.[DATE]
AND T.ROOM = T2.ROOM
AND T2.DATE_RANK<=50
WHERE T2.DATE IS NULL