SQL 不参与超大查询的并行性

tha*_*nby 9 sql-server parallelism

我有一个非常大的查询(约 630 行),它涉及大量嵌套SELECT语句并从多个视图中提取。我们的 SQL Server 将并行度设置为 2,阈值为 95(这样设置是因为我们的 DBA 正在根据其他一些应用程序对其进行优化)。此查询最近开始需要 5-10 分钟才能完成,而通常不到一分钟。在调查原因时,我们注意到它似乎永远不会触发并行,总是串行运行,并怀疑这可能与它的性能有关。奇怪的是,在实验过程中,我们甚至将阈值降回了默认值 5 秒,它仍然无法并行运行。什么可以阻止它?

我们一直在当时没有其他人使用的非生产环境中进行测试,因此这是唯一运行的查询。我们的DBA也尝试过清除缓存和计划,甚至回收系统,但都没有效果。

更新 1:根据评论,我已经确认统计数据每晚更新,但问题仍然存在。我们实际上将代码回滚到没有如此严重性能问题的早期版本,但将继续测试此代码,因为它应该提高旧代码的性能,并且在初始测试中确实做到了。将在此处相应地更新。

Pau*_*ite 19

奇怪的是,在实验过程中,我们甚至将阈值降回了默认值 5 秒,它仍然无法并行运行。什么可以阻止它?

优化器不会(或不能)生成并行计划的原因有很多。宽广地:

  1. 明显的原因,例如配置设置max degree of parallelism设置为 1,在具有 的资源调控器工作负载组下运行MAX_DOP = 1,或者只有一个逻辑处理器可用于 SQL Server
  2. 并行抑制操作

    有许多操作会阻止并行性,要么是因为它们在并行计划中没有意义,要么是因为产品(尚)不支持它们。一些迫使整个计划串行化的例子(并非详尽无遗!):

    • 修改表变量的内容(读取没问题)
    • 任何 T-SQL 标量函数(无论如何都是邪恶的)
    • 标记为执行数据访问的 CLR 标量函数(正常的没问题)
    • 一些内在的功能,包括OBJECT_NAMEENCYPTBYCERT,和IDENT_CURRENT
    • 快进光标
    • 系统表访问(例如sys.tables

    对具有使用非内联 T-SQL 标量函数的计算列的表(或视图)的任何引用都将导致串行计划,即使该列未在查询中引用

  3. 基数估计错误

    如果在目标查询中没有绝对阻止并行性的东西,优化器仍然可以选择具有较低估计成本的串行替代方案。这可能是由错误的基数估计引起的。

  4. 成本计算模型限制

    SQL Server 使用模型来估计查询计划中每个运算符的运行时成本。此模型可能不正确地花费比并行替代方案便宜的串行计划。优化器总是选择它认为最便宜的选项。

    当 SQL Server 花费一个并行计划时,它通常会将并行迭代器的 CPU 成本降低一个与预期运行时 DOP 相等的因子。带有嵌套循环连接的计划可能是一个特殊问题,因为内侧几乎总是串行运行多个线程。并行图标仍然存在,但它们表明存在独立于 DOP 的串行线程。

    区别可能是一个微妙的区别,但它 (a) 解释了为什么通常强制串行区域的操作符可以在循环连接的内侧“并行”运行;(b) 优化器不会通过估计的运行时 DOP 减少内部的 CPU 成本。与 Hash 和 Merge Joins 相比,这使嵌套循环在并行成本计算方面处于劣势,并且可以解释为什么优化器可能无法选择并行嵌套循环计划。

  5. 优化器代码路径问题

    优化器可能根本无法评估并行计划。发生这种情况的一种方式是在琐碎计划阶段找到最终计划。如果 Trivial Plan 是可能的,并且产生的成本小于为并行性配置的成本阈值,则跳过完整的优化阶段并立即返回串行计划。

    通过 Trivial Plan 的查询仍然可以提前终止优化(在考虑并行性之前),或者使用Good Enough Plan Found消息或Time Out。这两者都是启发式方法,以防止优化器花费更多的时间进行优化,而不是通过减少估计的执行时间(成本)获得。

测试

没有支持的方式来要求并行计划,但有一些未记录的技巧(不适合生产)。一种是临时将优化期间使用的 CPU 权重设置得更高,另一种是将跟踪标志设置为 8649。对于 SQL Server 2016 SP1 CU2 及更高版本,未记录的查询提示OPTION (USE HINT ('ENABLE_PARALLEL_PLAN_PREFERENCE'))执行与 TF 8649 相同的功能,但不需要管理员权限。

生成的计划可能不是优化器通常会考虑的计划,但您可以在经过仔细测试和审查后捕获它并在生产计划指南中使用它。

有关详细信息,请参阅Simon Sabin撰写的在 SQL Server 中强制执行并行查询执行计划不可并行化操作的文章。