我有一个查询,它之前执行得很慢。后来,我发现它不是并行运行的,这使得查询执行缓慢。
该查询涉及一个大的view,然后使用大量的temp tables和sub query查询视图。
我从视图中删除了一个UDF,使用了inline functions,也使用了标量TVF,然后它开始在parallel execution中快速运行。
几天都很顺利,有一天我注意到查询运行得很慢。所以我检查了执行计划,发现查询是在串行模式下执行的。我检查了查询的计划缓存,看到了很多涉及该视图的缓存计划。我删除了不平行的计划,然后查询运行得很快。
现在,我每天早上都这样做,以强制查询并行运行。
其他详情:
如何强制查询永远并行运行?
发布于 2018-07-16 21:38:19
乍一看,这听起来像是一个典型的参数嗅探问题。
Server为需要编译计划时调用的第一组参数构建一个执行计划,然后一天又一次重复使用该计划。您可以看到它们是什么参数--当您查看串行计划时,右键单击select语句,然后进入属性。在“属性”窗口中,查找参数,然后编译值。这将告诉您哪些值会产生串行计划。
为了迫使计划始终并行运行,您有几种不同的选项( Erland在我上面链接到的优秀帖子中介绍了其中许多选项),包括:
这只是一个快速的答案--但是更多的是阅读Erland的优秀帖子,应用程序慢,SSMS快,它解释了一个查询如何获得不同的计划,以及如何修复它。
发布于 2018-07-16 21:46:05
可能很难对您的问题给出准确的答案,因为我们不知道您的查询是什么样子的,但是您可以使用SQL 2016引入的QueryStore特性强制执行特定的计划。如果您使用的是较早版本的Server,或者不认为查询存储是您的解决方案,您可以尝试如下:
您还应该回顾以前关于这个主题的StackExchange的文章,例如SQL不涉及超大查询的并行性
发布于 2018-07-18 10:36:46
如果查询成本超过Cost Threshold of Parallelism值,且cost of the parallel plan小于cost of a serial plan,则将创建并使用并行计划。
在某些情况下,QO选择串行计划而不是并行计划,因为在这种情况下,parallel plan比serial plan更昂贵。例如,如果查询包含不能以并行模式运行的标量或关系运算符。
在某些情况下,由于信息不准确、统计数据陈旧、cardinality estimate差等原因,QO做出了错误的决策,因此串行计划的成本略高于parallel plan。
因此,QO仍然选择连续计划。
为了克服这个问题,可以优化查询并更新统计数据。
这有助于QO做出正确的决策。
我从视图中删除了一个UDF,使用了内联函数,还使用了一个标量TVF。
这些是值得欢迎的步骤,一旦您改进了查询,其中一些计划是并行的,查询性能就会提高。
因此,可能还有进一步改进查询的范围。
在优化查询和优化索引时,人们应该更加注意,而不是马上尝试Hint。
其他的事情,如使用提示,参数嗅探,选项(重新编译)已经讨论过了。
https://dba.stackexchange.com/questions/212378
复制相似问题