【问题标题】:How to SELECT every row that has a duplicate value of a field如何选择具有字段重复值的每一行
【发布时间】:2017-04-18 13:59:41
【问题描述】:

使用 PostgreSQL,我试图找到一种方法来选择 每一 行,该行与特定列的值重复。

例如,我的表格如下所示:

id   | username | email
1    | abc      | abc@test.com
2    | abc1     | abc@test.com
3    | def      | def@test.com
4    | ghi      | ghi@test.com
5    | ghi1     | ghi@test.com

我想要的输出将选择用户名和电子邮件,其中电子邮件计数 > 2:

abc   | abc@test.com
abc1  | abc@test.com
ghi   | ghi@test.com
ghi1  | ghi@test.com

我尝试过group by having,这让我接近了我想要的,但我不认为我想使用group by,因为这实际上会将行与重复值组合在一起,我仍然想显示包含重复值的单独行。

SELECT email FROM auth_user
GROUP BY email HAVING count(*) > 1;

这只会显示具有重复值的电子邮件:

abc@test.com
ghi@test.com

我可以使用SELECT email, count(*) FROM ... 将计数包含在其中,但这也不是我想要的。

我想我想要where count(email) > 1 之类的东西,但这给了我一个错误,说ERROR: aggregate functions are not allowed in WHERE

如何在不分组的情况下选择重复值?

使用解决方案更新

@GordonLinoff 发布了正确答案。但是为了满足我仅获取用户名和电子邮件字段的确切需求,我对他进行了一些修改(这应该是不言自明的,但发布以防其他人需要确切的查询)

select username, email
from (select username, email, count(*) 
      over (partition by email) as cnt
      from auth_user au
) au
where cnt > 1;

【问题讨论】:

    标签: sql postgresql duplicates


    【解决方案1】:

    如果你想要所有原始行,那么我建议使用count(*) 作为窗口函数:

    select au.*
    from (select au.*, count(*) over (partition by email) as cnt
          from auth_user au
         ) au
    where cnt > 1;
    

    【讨论】:

    • 我喜欢你在我发布问题后 5 秒内回答的方式。我想我需要更多地研究我的 SQL。我会在 11 分钟后接受你的回答。谢谢!
    【解决方案2】:

    您可能会发现这也很有帮助:

    select t1.*, t2.*
    from auth_user t1, auth_user t2
    where t1.id != t2.id
    and t1.email = t2.email
    

    【讨论】:

      猜你喜欢
      • 2021-03-09
      • 2012-02-17
      • 2015-05-24
      • 1970-01-01
      • 1970-01-01
      • 2012-03-04
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多