sql-server – 在IF EXISTS中包装查询使得它非常慢
|
我有以下查询: select databasename from somedb.dbo.bigtable l where databasename ='someval' and source <>'kt' and not exists(select 1 from dbo.smalltable c where c.source=l.source) 上述查询在三秒钟内完成. 如果上面的查询返回任何值,我们希望存储过程为EXIT,所以我重写如下: If Exists(
select databasename
from somedb.dbo.bigtable l where databasename ='someval' and source <>'kt'
and not exists(select 1 from dbo.smalltable c where c.source=l.source)
)
Begin
Raiserror('Source missing',16,1)
Return
End
然而这需要10分钟. 我可以像下面一样重写上面的查询,它也可以在不到3秒的时间内完成: select databasename
from somedb.dbo.bigtable l where databasename ='someval' and source <>'kt'
and not exists(select 1 from dbo.smalltable c where c.source=l.source
if @@rowcount >0
Begin
Raiserror('Source missing',1)
Return
End
上面重写的问题是上面的查询是更大的存储过程的一部分,它返回多个结果集.在C#中,我们遍历每个结果集并进行一些处理. 上面返回一个空的结果集,所以如果我采用这种方法,我必须改变我的C#并再次进行部署. 所以我的问题是,
以下是可能对您有所帮助的详细信息,如果您需要任何详细信息,请告知我们: >创建表和统计信息脚本以获得与我的相同的计划 Slow plan using Brentozar Paste the plan 注意:两个查询都是相同的(使用参数),唯一的区别是EXISTS(我可能在匿名时犯了一些错误). 表创建脚本如下: http://pastebin.com/CgSHeqXc – 小桌子统计 解决方法正如 Paul White在他的博客文章中所解释的那样: Inside the Optimizer: Row Goals In Depth EXISTS引入了一个行目标,它更喜欢NESTED LOOPS或MERGE JOIN而不是HASH MATCH
在您的查询中,这显然会引入嵌套循环并删除并行性,从而导致计划速度变慢. 因此,您可能需要找到一种方法来重写查询,而无需使用查询中的NOT EXISTS. 您可能会使用LEFT OUTER JOIN重写您的查询并通过测试NULL检查smalltable中没有行 If EXISTS(
SELECT databasename
FROM somedb.dbo.bigtable l
LEFT JOIN dbo.smalltable c ON c.source = l.source
WHERE databasename = 'someval'
AND source <> 'kt'
AND c.source IS NULL
)
您也可以使用EXCEPT查询,具体取决于您需要比较的字段数,如下所示: If EXISTS( SELECT source FROM somedb.dbo.bigtable l WHERE databasename = 'someval' AND source <> 'kt' EXCEPT SELECT source FROM dbo.smalltable ) 请注意,Aaron Bertrand有一篇博文providing reasons why he prefers NOT EXISTS,您应该阅读以了解其他方法是否更好,并了解NULL值的潜在正确性问题. 相关Q&答:IF EXISTS taking longer than embedded select statement (编辑:开发网_运城站长网) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |
- sql-server – sys.stats_columns不正确吗?
- 将图像存储在数据库中而不是文件系统中
- sql – 与在MS Access数据库中加入相关的问题
- sql-server – 何时在重建索引时使用sort_in_tempdb?
- SQL Server中怎么样实现数字辅助表?一文带你看懂
- .Net Core 下使用ZKWeb.System.Drawing实现验证码功能(图形
- sql-server – SQL Server差异(与交叉相反)
- 国内七家单位今起可查看微软操作系统源代码
- sql – 具有Desc / Asc排序的Order By子句的Case语句
- 飞利浦光存储资深技术专家涌入国内为哪般?

