我想在MySQL数据库中取出重复的记录。这可以用:

SELECT address, count(id) as cnt FROM list
GROUP BY address HAVING cnt > 1

结果是:

100 MAIN ST    2

我想要拖动它,以便它显示复制的每一行。喜欢的东西:

JIM    JONES    100 MAIN ST
JOHN   SMITH    100 MAIN ST

有什么想法可以做到吗?我试图避免做第一个,然后在代码中用第二个查询查找重复。


当前回答

另一个解决方案是使用表别名,如下所示:

SELECT p1.id, p2.id, p1.address
FROM list AS p1, list AS p2
WHERE p1.address = p2.address
AND p1.id != p2.id

在这种情况下,您真正要做的是获取原始的列表表,从中创建两个假装的表——p1和p2,然后在地址列上执行连接(第3行)。第4行确保相同的记录不会在结果集中多次出现(“重复重复”)。

其他回答

寻找重复地址比看起来要复杂得多,特别是当你要求准确性时。在这种情况下,一个MySQL查询是不够的…

我在SmartyStreets工作,在那里我们解决验证和重复数据删除等问题,我看到过很多类似问题的不同挑战。

有一些第三方服务会在列表中为你标记重复项。仅使用MySQL子查询来执行此操作不会考虑地址格式和标准的差异。美国邮政总局(USPS)有一定的指导方针来制定这些标准,但只有少数供应商获得了执行此类操作的认证。

因此,我建议您最好的答案是,例如,将表导出到CSV文件中,并将其提交给有能力的列表处理程序。其中一个是LiveAddress,它会在几秒钟到几分钟内自动为你完成。它将用一个名为“duplicate”的新字段和一个Y值标记重复的行。

会是这样的:

SELECT  t1.firstname t1.lastname t1.address FROM list  t1
    INNER JOIN  list t2 
    WHERE 
        t1.id < t2.id AND 
        t1.address = t2.address;

最快重复项删除查询过程:

/* create temp table with one primary column id */
INSERT INTO temp(id) SELECT MIN(id) FROM list GROUP BY (isbn) HAVING COUNT(*)>1;
DELETE FROM list WHERE id IN (SELECT id FROM temp);
DELETE FROM temp;

要快速查看重复的行,可以运行一个简单的查询

在这里,我正在查询表,并列出所有重复的行相同的user_id, market_place和sku:

select user_id, market_place,sku, count(id)as totals from sku_analytics group by user_id, market_place,sku having count(id)>1;

要删除重复的行,必须决定要删除哪一行。例如id较低(通常较旧)或其他日期信息。在我的情况下,我只是想删除较低的id,因为较新的id是最新的信息。

首先仔细检查是否正确的记录将被删除。在这里,我正在选择将被删除的副本中的记录(通过唯一id)。

select a.user_id, a.market_place,a.sku from sku_analytics a inner join sku_analytics b where a.id< b.id and a.user_id= b.user_id and a.market_place= b.market_place and a.sku = b.sku;

然后我运行delete查询来删除dupes:

delete a from sku_analytics a inner join sku_analytics b where a.id< b.id and a.user_id= b.user_id and a.market_place= b.market_place and a.sku = b.sku;

备份,双重检查,验证,验证备份,然后执行。

这将在一次表传递中选择重复项,没有子查询。

SELECT  *
FROM    (
        SELECT  ao.*, (@r := @r + 1) AS rn
        FROM    (
                SELECT  @_address := 'N'
                ) vars,
                (
                SELECT  *
                FROM
                        list a
                ORDER BY
                        address, id
                ) ao
        WHERE   CASE WHEN @_address <> address THEN @r := 0 ELSE 0 END IS NOT NULL
                AND (@_address := address ) IS NOT NULL
        ) aoo
WHERE   rn > 1

这个查询实际上模拟了Oracle和SQL Server中的ROW_NUMBER()

详见我博客上的文章:

分析函数:SUM, AVG, ROW_NUMBER -在MySQL模拟。