我需要运行一个查询来比较两个表并返回不在第二个表中的记录。棘手的部分是两个表之间的链接是有条件的。我有多个来源进入表2,然后进入表1。我尝试过使用连接,但这并不比我下面的更快。这些表中有大约5万条记录。此查询大约需要1.5分钟才能完成。我希望大约几秒钟。 Table1和Table2已经在这些字段上有索引。 DB在兼容级别SQL2008上运行。
此查询大约需要1.5分钟:
select *
from Table1 t1
where not exists (select *
from Table2 t2
where t2.seedID = case t2.SeedSource when 'SeedSource1' then t1.SeedSource1
when 'SeedSource2' then t1.SeedSource2
when 'SeedSource3' then t1.SeedSource3
when 'SeedSource4' then t1.SeedSource4
when 'SeedSource5' then t1.SeedSource5 end)
此查询需要五分钟:
select d.*
from Tabel1 t1 left join
Table2 t2 on t2.seedID = case t2.SeedSource when 'SeedSource1' then t1.SeedSource1
when 'SeedSource2' then t1.SeedSource2
when 'SeedSource3' then t1.SeedSource3
when 'SeedSource4' then t1.SeedSource4
when 'SeedSource5' then t1.SeedSource5 end
where t2.seedID is NULL
非常感谢任何帮助。
答案 0 :(得分:1)
阅读完您的要求后,您的查询就可以了。 (最佳做法是使用Not Exists
代替Not IN
和Left Join
)
您可以进行一些小优化:
WHERE
子句中使用not exists (select 1 ...
代替not exists (select * ...
,当您可以选择常量时,无需选择所有列。 (表现更好)<强>参考强>
答案 1 :(得分:1)
实际上它们不是同一个查询,因为左连接会在多个匹配项上返回多行
不存在是更好的方法
我希望SeedSource,SeedSource1-5和seedID被编入索引
select *
from Table1 t1
where not exists ( select *
from Table2 t2
where t2.seedID = t1.SeedSource1
and t2.SeedSource = 'SeedSource1'
union all
select *
from Table2 t2
where t2.seedID = t1.SeedSource2
and t2.SeedSource = 'SeedSource2'
//...
)
也许
left join Table2 t2
on ( t2.seedID = t1.SeedSource1 and t2.SeedSource = 'SeedSource1' )
or ( t2.seedID = t1.SeedSource2 and t2.SeedSource = 'SeedSource2' )
// ...
答案 2 :(得分:0)
也许:
SELECT t1.* FROM table1 t1 LEFT JOIN table2 t2 on t1.seedID = t2.seedID
WHERE t2.seedID is NULL AND t1.SeedSource IN ('SeedSource1','SeedSource2','SeedSource3','SeedSource4','SeedSource5')