数据库中的查询改写(query rewrite)把一个 SQL 改写成另外一个更加容易优化的 SQL。OceanBase 数据库的查询改写规则分为基于规则的查询改写和基于代价的查询改写。
基于规则的查询改写总是会把 SQL 往“好”的方向进行改写,从而增加该 SQL 的优化空间。一个典型的基于规则的改写是把子查询改写成连接,如果不改写,子查询的执行方式只能是 Nested Loop Join。 但是改写之后,优化器就也可以考虑Hash Join 和 Merge join 的执行方式。
基于代价的查询改写并不能总是把 SQL 往“好”的方向进行改写,所以需要代价模型来判断。一个典型的基于代价的改写就是 Or-expansion。
在数据库中,一个改写规则通常需要满足特定的条件才能够进行改写,而且很多规则的改写可以互相作用(一个规则的改写会触发另外一个规则的改写),所以在 OceanBase 数据库中,我们把能够互相作用的改写规则组织成一个规则集合。因为一个规则集合中的规则可以互相作用,所以 OceanBase 数据库采用迭代式的方式进行改写一直到 SQL 不能被改写为止或者迭代次数达到预先设定的阀值。
OceanBase 数据库把所有基于规则的查询改写分成若干个规则集合。对于每个规则集合,OceanBase 数据库采用迭代式的方式进行改写一直到 SQL 不能被改写为止或者迭代次数达到预先设定的阀值。类似地,对于基于代价的改写规则也是采用这种方式处理。这里需要注意的是,基于代价的改写之后可能又会重新触发基于规则的改写,所以整体上的基于代价的改写和基于规则的改写也会采用这种迭代式的方式进行改写。