写点什么

直播速递 | Plan Stitch:一种使用缝合物理计划解决查询计划性能退化问题的方法

作者:开务数据库
  • 2022-10-21
    上海
  • 本文字数:4192 字

    阅读完需:约 1 分钟


10 月 13 日,我们邀请西安高校计算机科学与技术学院韩松纬博士为大家带来分享《Plan Stitch:一种使用缝合物理计划解决查询计划性能退化问题的方法》

 

本期论文《Plan Stitch: Harnessing the Best of Many Plans》重点提出了 Plan Stitch 解决方案的框架与实现方式,全面介绍如何通过物理计划缝合的方式有效解决查询计划性能回退问题。

 

Part 1 论文背景

 

查询优化器选择了一个糟糕的执行计划而导致查询性能下降,是工作负载中的一个常见痛点。查询计划可能会因为各种原因而改变,比如创建删除索引、统计信息时,使用与上次不同的参数绑定重新编译存储过程、使用计划提示进行调优查询等。

 

通常优化器可以有效地利用新创建的索引和统计信息,并由此生成成本更低的查询计划。但有时优化器选择的最新查询计划的执行成本明显更高,这种情况称之为计划回退 (plan regress)。

 

计划回退问题对于应用程序来说是十分痛苦的,因为它很难调试。当计划大规模定期更改时,以自动方式检测和纠正计划回退变得至关重要。这种自动校正技术风险一定要控制在低水平,防止由于校正而使得执行成本更加恶化。

 

商业 DBMS 已经认识到这个问题的重要性,例如 Azure SQL DB 和 Microsoft SQL Server 中的自动计划校正功能会自动检测并校正计划回退。当计划由于计划更改而回退时,如果该查询先前执行的计划仍然有效,会使用先前执行的计划来解决计划回退问题。

 

这种基于回归的计划校正 (RBPC) 方法由其风险较低而在生产环境中具有一定的吸引力,但是 RBPC 忽略了在其他先前执行的计划中收集到的有效子计划的潜在宝贵信息,限制自己从中选择一个总体上成本最低的计划。

 

举例说明 >>

 


一个连接 4 条关系(A,B,C,D)的查询,初始生成的执行计划如图 (a) 所示,优化器选择哈希连接 (HJ),对所有关系进行全表扫描,连接顺序为 (((A,B),C),D)。

 

假设在 B 和 D 上创建了新的二级索引后,生成了新的执行计划如图 (b) 所示,优化器使用嵌套循环连接 (NLJ),对 B 和 D 使用了索引扫描,连接顺序为 (((C,B),A),D)。

 

由于优化器对 (C, B, A) 连接的成本估计错误。选择了计划 p2,执行后发现成本比之前 p1 更高。在 RBPC 策略下会回过头使用 p1 计划执行。然而这样的方式错过了一个更好的计划 — 如图 (c) 所示它结合了 p1 和 p2 的子计划。

 

针对上述问题,论文中提出了一个崭新的解决方案,其贡献主要如下:

 

  • 论文提出了 Plan Stitch,通过使用算子级别的执行成本来构建新的缝合计划,其执行成本比 RBPC 策略复用的计划更低,计划回退的风险也能得到有效规避;

  • 论文中提出了一种高效的、基于动态规划的方法,以最便宜的执行成本构建一个新计划;

  • 论文将 Plan Stitch 实现到微软的 SQL Server 之上,并使用 TPC-DS 基准测试完成了 3 组实际客户工作负载实验,证明了 Plan Stitch 的有效性。

 

Part 2 相关工作

 

在过去的几十年里,利用执行反馈来提高计划质量一直是备受关注的研究领域,以前的工作大致可以分为 3 类:

  • 利用观察到的查询表达式的基数来优化同一查询;

  • 利用观察到的基数来改善统计信息,以帮助其他更多查询;

  • 改善优化器的开销模型。

 

Plan Stitch 不同于上述方法,它直接依赖观察到的执行成本,而没有将开销估算解耦到基数估计和开销模型中。因此 Plan Stitch 可以避免基数估计、开销模型中的不准确性。通过 Plan Stitch 获得的结果,其执行成本大概路不会高于优化器返回的计划成本。

 

计划回归校正

如第 1 部分所述,Plan Stitch 改进了商业 DBMS 中使用的基于回归的计划校正技术。Plan Stitch 保留了低风险和低开销的理想特性,同时利用先前计划中的有效子计划来进一步提高计划的质量。与仅仅使用以前执行的计划相比,Plan Stitch 生成的计划性能通常要提升 2 个数量级。

 

查询提示

商业数据库通过查询提示,以限制 / 影响优化器的搜索空间。Microsoft SQL Server 支持查询提示,它可以影响计划的部分内容(算子的连接顺序、访问路径),甚至可以影响优化器按照提示信息构造出一个整个计划,Oracle 数据库和 IBM DB2 也提供类似的功能。虽然这些提供了一种影响优化器的方法,但识别哪种提示适合于提高哪些特定查询任务仍然依赖于人类专家,如 DBA。这样的做法不仅费事费力,而且往往容易出错。Plan Stitch 填补了这一空白,它从先前执行的计划中自动识别出较优的子计划。

 

探索替代计划

与或图 (AND-OR Graph) 表示一个搜索空间,允许探索备选方案。用与或图对计划进行编码,并修改图的叶和节点,以重用内部计划结构和查询优化器的成本,从而减少物理配置调优的开销。现有的工作优化参数化查询,并通过缓存计划和重用优化器对共享子表达式的成本来减少优化器的调用数量。Plan Stitch 专注于执行成本,并通过执行反馈提高计划质量。它构建了执行成本中最便宜的计划,同时可能与之前执行的计划不同,存在部分结构上的变化。

 

Part 3 Plan Stitch 框架概述

 


问题概述

给定一个查询实例 q,当前数据库配置 C 中可用的索引集 {Ik} 和 q 的一组不同的执行计划 {pi},这些计划的每个算子的执行成本在过去的执行中都有记录,Plan Stitch 为查询 q 构造一个执行成本最便宜的计划 p,要求 p 中的每个算子都可以在某个计划 pi∈P 中找到。

 

框架概述

图中显示了 Plan Stitch 如何与 DBMS 集成的逻辑架构,它如何获得其输入 (q,P,C),以及它如何通过其输出 (p) 影响优化器的计划选择。

 

Plan Stitch 在查询优化和执行的关键路径之外执行,可以作为外部客户端组件或 DBMS 中的后台线程。优化器为给定查询和当前配置 (从数据库元数据获得) 选择一个计划,然后执行该计划,并将其执行统计信息记录在存储库中。

 

执行统计信息包括计划结构及其算子级别的执行成本。随着时间的推移,存储库会为同一查询收集它的不同的执行计划。我们就可以触发计划缝合来寻找与优化器当前选择的计划相比可以降低执行成本的替代缝合计划。

 

最终通过强制缝合计划的 API,也就是计划提示的机制,实现限制优化器使用缝合计划作为新的执行计划。Plan Stitch 有两个主要部分:

 

  • 使用先前执行的同一查询的不同计划 P 的集合来识别和编码一个受限的搜索空间;

  • 使用计划 pi 每个算子的执行成本在搜索空间中构建总执行成本最小的缝合计划。

 

Part 4 Plan Stitch 的实现

 

构建约束搜索空间

Plan Stitch 首先将构造缝合计划的搜索空间限制在某些 pi 中出现的运算符上,生成这种受限搜索空间的主要挑战是:

  • 从不同的计划 pi 中识别等效的子计划;

  • 将这些等效的子计划紧凑地编码在一个结构中,以允许有效的搜索。

 


查询计划中的每个节点以及位于该节点上的子计划具有所需物理属性的逻辑表达式,例如,没有排序顺序的 A join B join C join D。如果两个子计划具有相同的逻辑表达式和所需的物理属性,则它们是等价的。

 

为解决搜索空间编码问题,论文使用了 AND-OR 图构造搜索空间。在 AND-OR 图中,每个 AND 节点对应于一个计划中的一个物理运算符。每个 OR 节点表示一个具有所需物理属性的逻辑表达式。AND 节点的子节点是 OR 节点,代表 AND 节点的子计划的逻辑表达和必要的物理属性。OR 节点的子节点是 AND 节点,代表 OR 节点的备选子计划的根物理运算符。

 

构造缝合计划

AND-OR 图有 2 个重要的属性:

  • 该图是非循环的,使 Plan Stitch 能够自下而上地递归构建最便宜的计划;

  • 至少有一个或节点: 查询的所有计划共享的根或节点。

 

基于上述属性,论文使用动态规划为 AND-OR 图中的每个 AND 节点和每个 OR 节点拼接最便宜的子计划,来构造从叶和节点到根或节点的最便宜的计划。具体算法流程如下图所示:

 


自底向上遍历每一个 OR 节点,对于它的子算子 op(AND 节点):

 

  • 如果 op 是叶节点:则 bestsubplan 是 op 本身,bestSubUnitCost 是执行一次 op 的成本;

  • 如果 op 是非叶节点:遍历每个子节点 (OR 节点) 的 bestSubInGp 缝合进 op,然后计算 op 的 stitchedSubUnitCost;

  • 最后在构造出以 op 为根的最便宜的缝合子计划后,更新相应的 bestSubInGp (g (or));

  • 在进行动态规划时用到了一个计算公式 stitchedSubUnitCost 用于估算缝合计划的成本。该公式输入有 4 个,其中 opCost 是观察到的算子的执行成本,execCount 是在其原始计划中被执行的次数,childSubUnitCost 是执行每个缝合的子计划的估计执行成本,childExecCount 是原始子计划的执行次数。

 

其次,论文中为估算缝合计划的成本还提出了 2 个假设:

 

  • 假设同一个逻辑运算的运算符,只要它的输入和输出不变,其执行成本可以从一个计划转移到另一个计划。

  • 对于多次执行的子计划,可以将执行成本平均分配给每次执行,从而第一个执行的启动开销。

 

基于上述公式和假设,论文通过自底向上的动态规划算法实现了缝合计划的搜索。

 

Part 5 实验结果

 

论文通过 TPC_DS 测试基准 (10 GB),分别在三例实际客户工作负载中进行了实验。实验比较了基于回归的计划校正 (RBPC) 和计划缝合 Plan Stitch 的性能,表 1 显示了工作负载的一些汇总统计信息:

 


论文从计划质量、开销估算、覆盖范围、Overhead、缝合计划分析、参数化查询、数据变化共 7 个方面分析 Plan Stitch 的性能,这里节选部分实验结果进行展示,感兴趣的读者可以阅读原文。

 

计划质量提升

 


图 4、5、6 和 7 显示了在 TPC-DS 基准和真实世界的客户工作负载中,缝合计划的执行成本比 RBPC 的改善的百分比。其中 x 轴的标签是下边界,y 轴是 Plan Stitch 被调用的百分比。

 

例如,图 4 显示,16% 的缝合计划的执行成本比 RBPC 选择的计划便宜 0%-10%。与 RBPC 选择的计划相比,Plan Stitch 在所有工作负载中至少有 40% 的缝合计划的执行成本进一步降低了 10%。

 

开销估算误差

 


图 9、10、11 和 12 显示了 TPC-DS 基准和真实世界客户工作负载中,缝合计划的开销估算误差分布。论文计算了缝合计划的执行成本与估计成本的比例,排除了执行成本和估算成本差异都很小的计划。

 

在所有的工作负载中,至少 70% 的缝合计划的开销估计值的误差在 20% 以内,证明了估算缝合子计划开销中描述的成本计算假设在实践中基本成立。

 

开务数据库 - 线上沙龙系列活动

 

如果你想了解数据库领域的最新动态、前沿技术干货、实战落地案例等,那么开务数据库线上沙龙系列活动,你值得拥有!

 

我们定期举办以技术、学术、培训等为主题的系列内容直播,欢迎大家来开务数据库 B 站直播间线上做客!让我们一起携手遨游在数据库知识的海洋!

 

扫码关注 “开务数据库” B 站号

直播不迷路↓ ↓ ↓



用户头像

还未添加个人签名 2021-04-29 加入

还未添加个人简介

评论

发布
暂无评论
直播速递 | Plan Stitch:一种使用缝合物理计划解决查询计划性能退化问题的方法_开务数据库_InfoQ写作社区