这是我在SQL Server中遇到的最奇怪的事情:
DB 1: 表A Id,FieldXYZ
表B Id,FieldXYZ
DB2: 表A ID,FieldXYZ
表B Id,FieldXYZ
Query 1 in DB1:
Select *, 'Unmapped' as Flag
FROM TableA
Where NOT EXISTS (Select * FROM TableB B JOIN TableA A ON ISNULL(B.XYZ,'')=ISNULL(A.XYZ,''))
Result:
Id , XYZ , Flag
23 unmapped ---- Field XYZ here is blank, not NULL, just blank
Query 1 in DB2:
Select *, 'Unmapped' as Flag
FROM TableA
Where NOT EXISTS (Select * FROM TableB B JOIN Table A ON ISNULL(B.XYZ,'')=ISNULL(A.XYZ,''))
Result:
Id , XYZ , Flag --- I don't get any results in the DB2 for the same data as DB1
如果我在DB1中修改我的查询,如下所示,那么我没有得到任何“未映射”的内容:
Query 2 in DB1:
Select *, 'Unmapped' as Flag
FROM TableA
Where NOT EXISTS (Select * FROM TableB B JOIN TableA A ON ISNULL(B.XYZ,'')=ISNULL(A.XYZ,'') OR A.XYZ = ' ') -- there is a space here in A.XYZ = ' '
如果在两个db中运行以下查询,我会从每个中获取一条记录:
SELECT * FROM DB1.dbo.TableA where FieldXYZ = ' ' -- space within quotes
SELECT * FROM DB2.dbo.TableA where FieldXYZ = ' ' -- space within quotes
那么db1中的查询1会发生什么?
答案 0 :(得分:0)
如果您希望TableA
中的所有记录与TableB
不匹配,那么您的查询是错误的。
你真的想要这个:
SELECT TableA.*, 'Unmapped' as Flag
FROM TableA
LEFT OUTER JOIN TableB
ON ISNULL(TableA.XYZ,'') = ISNULL(TableB.XYZ,''))
WHERE TableB.ID IS NULL
以下是您的查询正在执行的操作:
Select *, 'Unmapped' as Flag
FROM TableA
Where NOT EXISTS (
Select *
FROM TableB B
JOIN TableA A
ON ISNULL(B.XYZ,'')=ISNULL(A.XYZ,'')
)
TableA
与TableB
字段上的XYZ
匹配。TableA
。另一种选择是:
Select *, 'Unmapped' as Flag
FROM TableA
Where NOT EXISTS (
Select *
FROM TableB B
WHERE ISNULL(B.XYZ,'') = ISNULL(TableA.XYZ,'')
)
请注意,子查询引用回主查询中的TableA
。
答案 1 :(得分:0)
正如我在评论中提到的,如果你在两个数据库中只运行NOT EXISTS查询,你会看到这些数据库的结果有相同的差异。所以我的观点是问题不在“NOT EXISTS”子句中,它在查询中使用的“ISNULL”条件中。
这就是为什么我们不应该使用“ISNULL”函数来检查列的NULL值而是使用“IS NULL”子句。
Do not use ISNULL to find NULL values. Use IS NULL instead
如果您按如下方式更改查询,那么您应该很好并且看到相同的结果。
Select *
FROM TableB B
JOIN Table A ON
(CASE WHEN B.XYZ IS NULL THEN '' ELSE B.XYZ END)
=
(CASE WHEN A.XYZ IS NULL THEN '' ELSE A.XYZ END)