34,696
社区成员
发帖
与我相关
我的任务
分享
我有三个表,表名及数据分别如下 。其中表1和表3的数据量比较大,想要的结果是:从表1中查询出表1与表2没有完全组合在表3中的数据。
在下面的示例数据中,应该查询出的结果是:A,C,D,E,只有B与1、2、3的组合都在T3中了。
要求执行效率比较高,使用环境:MS SQL 2014。
谢谢!
表T1:
ID
A
B
C
D
E
表T2:
TH
1
2
3
表T3:
ID TH
A 1
A 2
B 1
B 2
B 3
C 1
C 3
D 2
E 2
E 3
数据量大的话我这种可能比其他人的要快些,因为少了的扫表和联接的开销。而且写法也相对简单明了。
create table #T2(TH int)
insert into #T2 VALUES(1),(2),(3)
create table #T3(ID nvarchar(50), TH int)
insert into #T3 VALUES ( 'A',1),( 'A',2),( 'B',1),( 'B',2),( 'B',3),( 'C',1),( 'C',3),
( 'D',2),( 'E',2),( 'E',3)
select ID from #T3 group by ID having count(*) <(select count(*) from #T2)
DECLARE @T1 TABLE (ID VARCHAR(10))
INSERT INTO @T1( ID )
VALUES ('A'),('B'),('C'),('D'),('E')
DECLARE @T2 TABLE (TH INT)
INSERT INTO @T2(TH)
VALUES(1),(2),(3)
DECLARE @T3 TABLE (ID VARCHAR(10),TH INT )
INSERT INTO @T3 ( ID, TH )
VALUES ( 'A',1),( 'A',2),( 'B',1),( 'B',2),( 'B',3),( 'C',1),( 'C',3),
( 'D',2),( 'E',2),( 'E',3)
SELECT T4.*
FROM (SELECT T1.ID,T2.TH FROM @T1 AS T1 CROSS JOIN @T2 AS T2) AS T4
LEFT JOIN @T3 AS T3 ON T4.ID = T3.ID AND T4.TH = T3.TH
WHERE T3.ID IS NULL
用的还可以
SELECT T1.ID
FROM T1
CROSS JOIN T2
LEFT JOIN T3 ON T1.ID = T3.ID AND T2.TH = T3.TH
GROUP BY T1.ID, T2.TH
HAVING COUNT(T3.ID) = 0
OR COUNT(DISTINCT T2.TH) OVER (PARTITION BY T1.ID) > COUNT(DISTINCT T3.TH) OVER (PARTITION BY T1.ID)
GROUP BY T1.ID
HAVING MAX(CASE WHEN COUNT(T3.ID) OVER (PARTITION BY T1.ID, T2.TH) = 0 THEN 1 ELSE 0 END) = 1;