删除除 Group 之外的所有 SQL 行

Posted

技术标签:

【中文标题】删除除 Group 之外的所有 SQL 行【英文标题】:Delete all SQL rows except one for a Group 【发布时间】:2021-12-30 21:02:46 【问题描述】:

我有一张这样的桌子:

架构 (MySQL v5.7)

CREATE TABLE likethis
    (`id` int, `userid` int, `date` DATE)
;
    
INSERT INTO likethis
    (`id`, `userid`, `date`)
VALUES
        (1, 1, "2021-11-15"),
        (2, 2, "2021-11-15"),
        (3, 1, "2021-11-13"),
        (4, 3, "2021-10-13"),
        (5, 3, "2021-09-13"),
        (6, 2, "2021-09-13");

id userid date
1 1 2021-11-15
2 2 2021-11-15
3 1 2021-11-13
4 3 2021-10-13
5 3 2021-09-13
6 2 2021-09-13

View on DB Fiddle

我想删除所有超过 14 天的记录,除非用户只有更旧的记录 - 而不是为该用户保留“最新”(最大“id”)行。

该操作后的预期目标应为:


id userid date
1 1 2021-11-15
2 2 2021-11-15
3 1 2021-11-13
4 3 2021-10-13

即:用户 ID 1 仅在过去 14 天内有记录:保留所有记录。用户 ID 在过去 14 天内有记录,因此删除所有超过 14 天的记录。用户 ID 3 只有“旧”记录,即超过 14 天 - 因此只保留这些记录中最新的一条,即使它超过 14 天。

我想到了一个类似于子查询的自我加入,我按用户 ID 分组......但无法真正做到......

【问题讨论】:

【参考方案1】:

相信你可以在MySql中使用case函数

例如-

SELECT TableID, TableCol,
CASE
    WHEN Date > 30 THEN "Delete statement"
    ELSE "Dont Delete (Record is not 30"
END
FROM TableName;

推荐链接:

    https://www.w3schools.com/sql/func_mysql_case.asp https://dev.mysql.com/doc/refman/5.7/en/case.html

希望这会有所帮助...

【讨论】:

【参考方案2】:

这个查询可以工作

DELETE b
FROM likethis a
JOIN likethis b ON a.`userid` = b.`userid` AND a.`date` > b.`date`
WHERE b.`date` < NOW() - INTERVAL 14 DAY

【讨论】:

看起来还不错,虽然我不太理解这个查询?。 db-fiddle.com/f/btrgFx7VJFAfL22PDyMhSq/13 这是添加的测试用例,其中包含更多数据。 @tim 如果日期是 14 天前,它会删除一条记录 b,并且同一用户必须有另一条记录 a 更新,所以如果用户的所有记录都是 14天前,只有最新的记录不满足b的条件,被排除在删除之外。

以上是关于删除除 Group 之外的所有 SQL 行的主要内容,如果未能解决你的问题,请参考以下文章

删除除具有最大值的行之外的所有行

如何从表中删除除前两个和最后一个之外的所有行?

TSQL - 每组删除除 1 之外的所有行

SQL查询:从表中删除除最新N之外的所有记录?

SQL Server:删除除最新的“n”个结果之外的所有结果

jQuery删除除第一行之外的所有表行