一、背景
查询优化器在查询中无疑是重要的部分,相同的查询目的,一个好的查询计划和坏的查询计划,查询时长、消耗系统资源可以相差几十倍以上;查询使用的时间资源和机器资源都是金钱,优化查询计划无疑是节省成本最好的方法;
在查询引擎发展的过程中,论文The Volcano Optimizer Generator : Extensibility and Efficient Search,The Cascades Framework for Query Optimization具有开创性的意义;尽管现在看来,火山模型有些地方已经过时,但是目前很多的查询engine都是基于火山模型开发和改造的,比如calcite、presto、spark;
不过以上两篇论文都比较晦涩难懂,如果想要了解查询优化如何做的,推荐阅读论文《EFFICIENCY IN THE COLUMBIA DATABASE QUERY OPTIMIZER》,相对容易很多;
二、优化器的基本概念
查询优化的定义:给定查询意图和代价模型,搜索查询计划空间的所有实现可能,得到代价最低的执行计划。
搜索查询计划是一个NP hard问题,可以使用动态规划解决;
- Operator
描述特定的运算符,比如Join/Aggregation,分为logical/physical两种;Logical Operator描述逻辑语义,Physical Operator描述算子,例如Join有hash Join/nested loop join - Expression
表达式,在计划空间中一个数据结构,内部包含Operator - logical property
逻辑属性,与运算语义相关的属性,比如:schema,cardinality; - physical property
物理属性,与具体实现相关的属性,比如:collation,distribution - group
逻辑等价组,其中包含相同逻辑输出属性的Expression - search space
全局的容器,在代价空间搜索的过程中,生成新的group/expression/operator都包含在查询空间中,查询空间类似Hash表,能够消除相同的元素 - Pattern
模式,描述具有某种形状的计划树 Ast,在应用规则的时候,需要对Ast语法树模式匹配; - Rule
规则是搜索算法中最核心部分,Rule应用的到logical expression,转换成另一种logical expression。其中logical -> logical的转换,是transformation rule;logical -> physical的转换,是implementation rule;其中Pattern是会匹配的表达式形态,Substitute是表达式替换之后的形态;
- enforcer
在ast从上到下的搜索过程中,先处理parent再处理children,例如parent implement为 sort merge join,则要求child输出的结果在join key上有序,若是child输出的output无序,则需要强制增加sort算子排序child的结果;enforcer是物理算子,作用是改变input group的物理属性;
三、Columbia查询优化器
Columbia优化器也是火山引擎的一种实现方式,我主要参考论文《EFFICIENCY IN THE COLUMBIA DATABASE QUERY OPTIMIZER》和这篇文章
3.1 Search Space(SSP)
3.1.1 muti-expr
SSP中由multi-expression(multi-expr)组成, 看名字就知道multi-expr能起代表多个expr的功能,multi-expr和expr都由Operator组成,multi-expr 输入是子group,expr的输入是子expr(这里的输入是指计算时数据的流向);发明multi-expr的这个概念的作用主要是为了方便于算法在SSP中搜索最佳的计划;在构建SSP时,会将输入的查询AST拷贝到SSP中,生成一个与AST一一对应的结构;
operator
|-> other operator
其中的operator转化成类似如下:
SSP (Search Space)
|-> groups (array)
|-> m-exprs
|-> operator (logical/physical)
|-> input groups (array)
3.1.2 优化过程
Columbia查询优化器定义5种类型的Task去遍历查询AST,遍历的同时转换查询计划,将更多可能的查询计划加入SSP中,最后根据代价模型,找出代价最小的查询计划;五种任务分别是:
- O_GROUP
- O_EXPR
- E_GROUP
- APPLY_RULE
- O_INPUTS 每执行一个任务,根据查询的AST和Rule都可能引入新的任务;关系图是:
3.1.3 总结
- 开始在SSP中初始化basic group,每个group包含一个m-expr,与AST中的expr一一对应
- 对root节点执行O_GROUP任务,会对group中的m-expr调用O_EXPR, 生成logical m-expr和physical m-expr;并优先对physical m-expr生成O_INPUT任务,优先得到physical plan(得到其cost),并用得到的cost更新SSP中的cost upper bound,帮助搜索过程快速剪枝;
- 新生成logical m-expr会继续调用O_EXPR任务,生成更多的logical m-expr和physical m-expr,在SSP中扩展出更多的表达式,丰富SSP空间;扩展方式主要有:在现有的group中增加m-expr,或者生成新的group加入SSP空间中
- 生成过程中,针对每一个节点(subplan)都会生成一个winner,并且返回上层汇总,最终ROOT汇总出全局的最优解;