在这种情况下如何删除重复的行?

时间:2013-04-29 16:02:23

标签: mysql

|  id  |        name        |              date           |     points   |
|  10  |        Paul        |     2013-04-29 10:15:03     |       2      |
|  11  |       Joseph       |     2013-04-29 10:50:17     |       0      |
|  12  |       Joseph       |     2013-04-29 11:23:18     |       10     |
|  13  |        Bill        |     2013-04-29 11:27:10     |       8      |
|  14  |        Paul        |     2013-04-29 11:41:38     |       5      |
|  15  |       Joseph       |     2013-04-29 11:43:15     |       0      |
|  16  |       Joseph       |     2013-04-29 11:47:30     |       0      |
|  17  |       Joseph       |     2013-04-29 12:51:38     |       0      |
|  18  |       Joseph       |     2013-04-29 12:53:58     |       10     |
|  19  |        Bill        |     2013-04-29 13:17:10     |       8      |
|  20  |       Joseph       |     2013-04-29 13:21:38     |       7      |

只能删除寄存器16和17。

我需要的是每次来自同一个用户的序列都是0时,所有相同的序列都被删除,除了第一个0,在这种情况下,id号为15。

1 个答案:

答案 0 :(得分:2)

假设date字段始终为增量,您可以按照下一步骤

进行操作
  1. 跟踪重复记录和这些记录的最短日期
  2. 删除日期值大于最小日期的所有记录。
  3. 代码示例:

    第1步:

    select name, points, count(id) as rowCount, min(id) as minId, min(`date`) as minDate
    from yourTable
    where points = 0
    group by name
    having count(id)>1
    

    第2步:

    delete from yourTable
    where id in (
        select id
        from yourTable
        inner join (
                select name, points, min(id) as minId, count(id) as rowCount, min(`date`) as minDate
                from yourTable
                where points = 0
                group by name
                having count(id) > 1
            ) as a on yourTable.name = a.name and yourTable.id > a.minId
        )
    and points = 0;
    

    希望这有帮助


    我认为使用临时表来获取要删除的ID可能很有用:

    -- Step 1: Create a temporary table with the names of the people you want to remove
    drop table if exists temp_dup_names;
    create temporary table temp_dup_names
        select name, points, min(id) as minId, count(id) as rowCount, min(`date`) as minDate
        from yourTable
        where points = 0
        group by name
        having count(id) > 1;
    alter table temp_dup_names
        add index idx_name(name),
        add unique index idx_id(minId);
    
    -- Step 2: Create a temporary table with the ids you want to delete
    drop table if exists temp_ids_to_delete;
    create temporary table temp_ids_to_delete
        select distinct a.id
        from yourTable as a
        inner join temp_dup_names as b on a.name=b.name and a.id > b.minId
        where points = 0;
    alter table temp_ids_to_delete
        add unique index idx_id(id);
    
    -- Step 3: Delete the rows
    delete from yourTable
    where id in (select id from temp_ids_to_delete);
    -- If MySQL is configured in 'safe mode', you may need to add this 
    -- to the where condition:
    -- and id > 0;