我找到了Jeff Smith的解决方案,它显示了两个表之间的差异:
SELECT MIN(TableName) as TableName, ID, COL1, COL2, COL3 ...
FROM
(
SELECT 'Table A' as TableName, A.ID, A.COL1, A.COL2, A.COL3, ...
FROM A
UNION ALL
SELECT 'Table B' as TableName, B.ID, B.COL1, B.COl2, B.COL3, ...
FROM B
) tmp
GROUP BY ID, COL1, COL2, COL3 ...
HAVING COUNT(*) = 1
ORDER BY ID
在我的项目中,我需要比较一下。仅限col1和col2,rest用于其他操作。 我试着用
HAVING (COUNT(col1) = 1 and COUNT(col2) = 1)
但没有效果。
你能否请我解决这个问题?
答案 0 :(得分:3)
使用以下COL1
获取COL2
中A
和B
的{{1}}值
SELECT COL1, COL2 FROM A
EXCEPT
SELECT COL1, COL2 FROM B
将结果用作派生表,将它们连接回A
并获取所有列:
SELECT 'A' AS SRC, A.COL1, A.COL2, A.COL3...
FROM (
SELECT COL1, COL2 FROM A
EXCEPT
SELECT COL1, COL2 FROM B
) AS diff
INNER JOIN A ON diff.COL1 = A.COL1 AND diff.COL2 = A.COL2
同样,使用EXCEPT获取仅存在于COL1
中的COL2
和B
的值,并将结果集合加入B
以获取完整的行相应
将两组与UNION ALL结合使用:
SELECT 'A' AS SRC, A.COL1, A.COL2, A.COL3...
FROM (
SELECT COL1, COL2 FROM A
EXCEPT
SELECT COL1, COL2 FROM B
) AS diff
INNER JOIN A ON diff.COL1 = A.COL1 AND diff.COL2 = A.COL2
UNION ALL
SELECT 'B' AS SRC, B.COL1, B.COL2, B.COL3...
FROM (
SELECT COL1, COL2 FROM B
EXCEPT
SELECT COL1, COL2 FROM A
) AS diff
INNER JOIN B ON diff.COL1 = B.COL1 AND diff.COL2 = B.COL2
;
答案 1 :(得分:0)
您正在从错误的位置删除列。您应该从列列表中删除它,而不是从列中删除它:
SELECT MIN(TableName) as TableName, ID, COL1, COL2
FROM
(
SELECT 'Table A' as TableName, A.ID, A.COL1, A.COL2
FROM A
UNION ALL
SELECT 'Table B' as TableName, B.ID, B.COL1, B.COl2
FROM B
) tmp
GROUP BY ID, COL1, COL2
HAVING COUNT(*) = 1
ORDER BY ID
要保留结果中的其他列,您可以使用MIN
(或朋友)来保留它们:
SELECT MIN(TableName) as TableName, ID, COL1, COL2, MIN(COL3), MIN(COL4), ...
FROM
(
SELECT 'Table A' as TableName, A.ID, A.COL1, A.COL2, A.COL3, A.COL4, ...
FROM A
UNION ALL
SELECT 'Table B' as TableName, B.ID, B.COL1, B.COL2, B.COL3, B.COL4, ...
FROM B
) tmp
GROUP BY ID, COL1, COL2
HAVING COUNT(*) = 1
ORDER BY ID
请注意,这在某些情况下效果不佳。如果两个表中的两行相同(包括ID),那么即使它不是,它也会发现它有差异。此外,在此版本中,如果您有多个行COL1
和COL2
相同,那么这也不行。我会将这两张表加在一起,以便进行更有力的比较。