在sql中查找两个表之间的重复差异

rgb*_*rgb 1 sql t-sql sql-server sql-server-2012

我试图在两个表之间找到重复的行.此代码仅在记录不重复时有效:

(select [Name], [Age] from PeopleA
except
select [Name], [Age] from PeopleB)
union all
(select [Name], [Age] from PeopleB
except
select [Name], [Age] from PeopleA)
Run Code Online (Sandbox Code Playgroud)

如何查找丢失的重复记录.Robert 34PersonA表中,例如下面:

人物A:

Name   | Age
-------------
John   | 45
Robert | 34
Adam   | 26
Robert | 34
Run Code Online (Sandbox Code Playgroud)

人B:

Name   | Age
-------------
John   | 45
Robert | 34
Adam   | 26
Run Code Online (Sandbox Code Playgroud)

Tim*_*ter 5

您可以使用UNION ALL连接表和Group Bywith Having子句来查找重复项:

SELECT x.Name, x.Age, Cnt = Count(*) 
FROM (   
    SELECT a.Name, a.Age
    FROM PersonA a

    UNION ALL

    SELECT b.Name, b.Age
    FROM PersonB b  
) x
GROUP BY x.Name, x.Age
HAVING COUNT(*) > 1
Run Code Online (Sandbox Code Playgroud)

根据您的澄清的评论,你可以使用下面的查询来查找所有名年龄组合,PersonA这是不同的PersonB:

WITH A AS(
   SELECT a.Name, a.Age, cnt = count(*)
   FROM PersonA a
   GROUP BY a.Name, a.Age
),
B AS(
   SELECT b.Name, b.Age, cnt = count(*)
   FROM PersonB b
   GROUP BY b.Name, b.Age
)
SELECT a.Name, a.Age
FROM A a LEFT OUTER JOIN B b
  ON a.Name = b.Name AND a.Age = b.Age
WHERE a.cnt <> ISNULL(b.cnt, 0)
Run Code Online (Sandbox Code Playgroud)

演示


如果你也想找到一个PersonBPersonA你身边但不在你身边的人应该使用FULL OUTER JOIN像戈登·林诺夫所评论的:

WITH A AS(
   SELECT a.Name, a.Age, cnt = count(*)
   FROM PersonA a
   GROUP BY a.Name, a.Age
),
B AS(
   SELECT b.Name, b.Age, cnt = count(*)
   FROM PersonB b
   GROUP BY b.Name, b.Age
)
SELECT Name = ISNULL(a.Name, b.Name), Age = ISNULL(a.Age, b.Age)
FROM A a FULL OUTER JOIN B b
  ON a.Name = b.Name AND a.Age = b.Age
WHERE ISNULL(a.cnt, 0) <> ISNULL(b.cnt, 0)
Run Code Online (Sandbox Code Playgroud)

演示