SQL:如何根据条件从表中删除行

时间:2017-10-09 13:23:40

标签: mysql sql sql-delete

我有下表:

tbl
source    type    date
---       ---     ---
google    A       2010-02-25
google    A       2013-04-11
facebook  C       2008-10-22
facebook  C       2007-01-28

我想只保留每个源的一个条目,并且标准是使用min(date) group by source选择源元组。该表由数百万条记录组成,我正在寻找一种删除冗余记录的有效方法。

4 个答案:

答案 0 :(得分:2)

在MySQL中,您可以使用join

执行此操作
delete t
    from t join
         (select source, min(date) as mindate
          from t
          group by source
         ) tt
         on t.source = tt.source
    where t.date > tt.mindate;

唯一的方法 - 我可以考虑使其更有效率的方法是将聚合结果存储在子查询中并为其添加索引。

我还可以补充一点,无论用于确定要删除的行的计算如何,都会以低效率删除表中的大量行。通常,我会建议采用三步法:

  1. 编写查询以生成所需的表,并将结果存储在临时表中。
  2. 截断原始表格。
  3. 重新插入(多)少量行。

答案 1 :(得分:0)

在Microsoft SQL中,您可以尝试此操作。

;
WITH cte 
        AS (SELECT ROW_NUMBER() OVER (PARTITION BY source, type
                                        ORDER BY createdate) RN
            FROM   tbsource)
DELETE FROM cte
WHERE  RN > 1;

答案 2 :(得分:0)

delete from t where date not in (select al.d from (select min(date) as d  from t group by source )al);

答案 3 :(得分:0)

将标识列作为序列号添加到重复表中,该序列号充当行唯一标识符(自动增量升序):

 alter table tbl add sno int identity(1,1)

table

此查询仅选择带有min(date)的非重复行:

(select min(date),sno From tbl group by source) 

所以“sno”将等于“1”和“4”。

现在加入此表,并删除重复的连接记录(t.sno为null)

delete E from tbl E
    left join
    (select min(date),sno From tbl group by source) T on E.sno=T.sno
where T.sno is null

table3

根据此链接的方法3改编的解决方案:LINK