这对我来说是一个有趣的转折,在另一张桌子上找到了无与伦比的记录"通常用左连接/空检查解决的问题。在我的搜索中,我没有在论坛中找到答案。
我有一个表A和一个表B,每个表都有相同的字段A和B.A是一个字符串,B是一个整数。
+-------------------+ +-------------------+
| Table A | | Table B |
| Field A | Field B | | Field A | Field B |
+---------+---------+ +---------+---------+
| A | 1 | | B | 1 |
| A | 2 | | B | 2 |
+---------+---------+ | B | 3 |
| B | 4 |
+---------+---------+
因此我运行的查询需要生成如下结果列表:
+-------------------+
| Table A |
| Field A | Field B |
+---------+---------+
| A | 3 |
| A | 4 |
+---------+---------+
我可以清楚地使用左/右连接将值(2,3,4)与B中的表A隔离;但是,当我在表B中使用纯设置操作在表A中没有匹配的记录时,我正在努力学习如何从表A获得字段A.例如,以下代码获取了FieldB的全部内容,但FieldA为null。
SELECT
TableA.FieldA
,TableB.FieldB
FROM
TableA
RIGHT JOIN TableB ON TableA.FieldB = TableB.FieldB
重要的是,我必须使用set操作执行此操作,因此没有WHILE构造,通过插入等的中间/临时表等。
我感谢任何指导/建议。
谢谢!
更新:
感谢您的快速帖子。几个人提到使用<>在内连接上。我最初是在几次测试中做到的,得到了表格的笛卡尔积,结果证明是大量的记录。我离开那个解决方案大约2个小时。这些帖子重燃了火。
所以我再次尝试了它并在查询中添加了GROUP BY子句。但是,出于某种原因,我仍然看到有相似之处的记录。所以,我不得不删除两个表有共同记录的记录。最终的SQL如下:
SELECT
FieldA
,FieldB
FROM
TableA
INNER JOIN TableB ON TableA.FieldB <> TableB.FieldB
WHERE
FieldB NOT IN (SELECT TableB.FieldB FROM TableB INNER JOIN TableA ON TableA.FieldB = TableB.FieldB)
GROUP BY
FieldA
,FieldB
这似乎没问题......
更新#2:
这里有另一个更新的实际表格结构,因为我的原始帖子似乎不清楚。请注意,我可以使用此代码重新创建我描述的问题的确切发生和解决方案:
CREATE TABLE #tblControlData
(
fldCN int
);
CREATE TABLE #tblCompData
(
fldCompanyID int
,fldCN int
);
INSERT INTO #tblControlData (fldCN) VALUES(1);
INSERT INTO #tblControlData (fldCN) VALUES(2);
INSERT INTO #tblControlData (fldCN) VALUES(3);
INSERT INTO #tblControlData (fldCN) VALUES(4);
INSERT INTO #tblControlData (fldCN) VALUES(5);
INSERT INTO #tblControlData (fldCN) VALUES(6);
INSERT INTO #tblControlData (fldCN) VALUES(7);
INSERT INTO #tblControlData (fldCN) VALUES(8);
INSERT INTO #tblControlData (fldCN) VALUES(9);
INSERT INTO #tblCompData (fldCompanyID,fldCN) VALUES(34,1);
INSERT INTO #tblCompData (fldCompanyID,fldCN) VALUES(34,2);
INSERT INTO #tblCompData (fldCompanyID,fldCN) VALUES(34,3);
SELECT
#tblCompData.fldCompanyID
,#tblControlData.fldCN
FROM
#tblCompData
CROSS JOIN #tblControlData
WHERE
#tblControlData.fldCN NOT IN (SELECT fldCN FROM #tblCompData)
GROUP BY
#tblCompData.fldCompanyID
,#tblControlData.fldCN
DROP TABLE #tblControlData
DROP TABLE #tblCompData
如果您只在此表上运行交叉联接,则会获得笛卡尔积,这是不正确的。那么然后添加GROUP BY,它仍然是不对的。然后用NOT IN减去公共项目,这是正确的。
结果如下:
fldCompanyID fldCN
34 4
34 5
34 6
34 7
34 8
34 9
我已经有一段时间了,而且我的思绪已经被炒了,但是如果你们都看到了更好的方式,我会接受建议。
谢谢!
答案 0 :(得分:0)
样本表
SELECT * INTO A
FROM
(
SELECT 'A' [Field A] ,1 [Field B]
)TAB
SELECT * INTO B
FROM
(
SELECT 'B' [Field A] ,1 [Field B]
UNION ALL
SELECT 'B' [Field A] ,2 [Field B]
UNION ALL
SELECT 'B' [Field A] ,3 [Field B]
UNION ALL
SELECT 'B' [Field A] ,4 [Field B]
)TAB
<强> QUERY 强>
SELECT A.[Field A],B.[Field B]
FROM A
CROSS JOIN B
WHERE A.[Field B]<>B.[Field B]
答案 1 :(得分:0)
最终的SQL如下:
SELECT
FieldA
,FieldB
FROM
TableA
INNER JOIN TableB ON TableA.FieldB <> TableB.FieldB
WHERE
FieldB NOT IN (SELECT TableB.FieldB FROM TableB INNER JOIN TableA ON TableA.FieldB = TableB.FieldB)
GROUP BY
FieldA
,FieldB
这个更紧凑......
SELECT
#tblCompData.fldCompanyID
,#tblControlData.fldCN
FROM
#tblCompData
CROSS JOIN #tblControlData
WHERE
#tblControlData.fldCN NOT IN (SELECT fldCN FROM #tblCompData)
GROUP BY
#tblCompData.fldCompanyID
,#tblControlData.fldCN
令人惊讶的是睡眠提供的清晰度......
以下答案运行得更快......
CREATE TABLE #tblControlData
(
fldCN int
);
CREATE TABLE #tblCompData
(
fldCompanyID int
,fldCN int
);
INSERT INTO #tblControlData (fldCN) VALUES(1);
INSERT INTO #tblControlData (fldCN) VALUES(2);
INSERT INTO #tblControlData (fldCN) VALUES(3);
INSERT INTO #tblControlData (fldCN) VALUES(4);
INSERT INTO #tblControlData (fldCN) VALUES(5);
INSERT INTO #tblControlData (fldCN) VALUES(6);
INSERT INTO #tblControlData (fldCN) VALUES(7);
INSERT INTO #tblControlData (fldCN) VALUES(8);
INSERT INTO #tblControlData (fldCN) VALUES(9);
INSERT INTO #tblCompData (fldCompanyID,fldCN) VALUES(34,1);
INSERT INTO #tblCompData (fldCompanyID,fldCN) VALUES(34,2);
INSERT INTO #tblCompData (fldCompanyID,fldCN) VALUES(34,9);
SELECT
#tblInterim.fldCompanyID
,#tblInterim.fldControlCN
FROM
(
SELECT
#tblCompData.fldCompanyID
,#tblTemp.fldCN AS fldControlCN
FROM
#tblCompData
CROSS APPLY
(
SELECT
fldCN
FROM
#tblControlData
) AS #tblTemp
GROUP BY
#tblCompData.fldCompanyID
,#tblTemp.fldCN
) AS #tblInterim
WHERE
#tblInterim.fldControlCN NOT IN (SELECT fldCN FROM #tblCompData WHERE #tblInterim.fldCompanyID = #tblCompData.fldCompanyID)
GROUP BY
#tblInterim.fldCompanyID
,#tblInterim.fldControlCN
DROP TABLE #tblControlData
DROP TABLE #tblCompData