参考:http://dev.mysql.com/doc/refman/5.7/en/subquery-optimization.html
一 引子
在上述参考中,有这样的话:
这是在说:
1 对于“
2 对于“
但是,其中提到了“
二 问题
我们暂且不提这个问题,先从整体上,理解一下子查询通常的优化方式,然后再来谈 MySQL的“
在“ToprowDB Dynamic Server 查询优化技术---子查询优化--03-1”一文中,介绍了优化的技术的本质,先读这一篇文章,有助于了解子查询优化技术。
总结子查询的优化方式,通常如下:
F1 使用semi-ji on来优化子查询,即把 子查询消除,上拉后使用“半连接”操作符来做表的连接,这是最常规的优化方式
F2 对于不可semi-jion(不全是这样,但多数是)的子查询,如果是非相关子查询,则物化子查询,这也是比较常用的优化方式
F3 对于不可优化的子查询,则连接时依旧存在子查询,这样的方式,其实是没有做优化的
三 更多细节问题
但是,子查询优化的细节,还有很多,例如:
1 “ A semi B”是否能够变为“B JION A”?
2 “ A semi B”对于B使用什么样的物理操作符?如果B上存在索引,是否可以利用索引?
3 MySQL的semi jion的策略怎么有5个(DuplicateWeedout、FirstMatch、LooseScan、Materializelookup、MaterializeScan)?
这些内容将来单独成文进行探讨。
四 EXISTS优化策略辨析
回到我们在文章初始提出的问题:
MySQL的“
首先,意味着是前述的"F1":
1 首先,子查询本质上没有被优化
2 但是,子查询被做了一些调整,调整的方式在开篇给出的链接中给出( http://dev.mysql.com/doc/refman/5.7/en/subquery-optimization.html),我们摘录如下:
对于如下的子查询,
一 引子
在上述参考中,有这样的话:
The MySQL query optimizer has different strategies available to evaluate subqueries. For IN
(or =ANY
) subqueries, the optimizer has these choices:
Semi-join
Materialization
EXISTS
strategy
For NOT IN
(or <>ALL
) subqueries, the optimizer has these choices:
Materialization
EXISTS
strategy
这是在说:
1 对于“
IN
(or =ANY
)”类型的子查询,有3种优化策略
2 对于“
NOT IN
(or <>ALL
)”类型的子查询,有2种优化策略
但是,其中提到了“
EXISTS
strategy”,有朋友问,
这个“EXISTS
strategy”是什么含义?
二 问题
我们暂且不提这个问题,先从整体上,理解一下子查询通常的优化方式,然后再来谈 MySQL的“
EXISTS
strategy”是什么含义?在“ToprowDB Dynamic Server 查询优化技术---子查询优化--03-1”一文中,介绍了优化的技术的本质,先读这一篇文章,有助于了解子查询优化技术。
总结子查询的优化方式,通常如下:
F1 使用semi-ji on来优化子查询,即把 子查询消除,上拉后使用“半连接”操作符来做表的连接,这是最常规的优化方式
F2 对于不可semi-jion(不全是这样,但多数是)的子查询,如果是非相关子查询,则物化子查询,这也是比较常用的优化方式
F3 对于不可优化的子查询,则连接时依旧存在子查询,这样的方式,其实是没有做优化的
三 更多细节问题
但是,子查询优化的细节,还有很多,例如:
1 “ A semi B”是否能够变为“B JION A”?
2 “ A semi B”对于B使用什么样的物理操作符?如果B上存在索引,是否可以利用索引?
3 MySQL的semi jion的策略怎么有5个(DuplicateWeedout、FirstMatch、LooseScan、Materializelookup、MaterializeScan)?
这些内容将来单独成文进行探讨。
四 EXISTS优化策略辨析
回到我们在文章初始提出的问题:
MySQL的“
EXISTS
strategy”是什么含义?首先,意味着是前述的"F1":
1 首先,子查询本质上没有被优化
2 但是,子查询被做了一些调整,调整的方式在开篇给出的链接中给出( http://dev.mysql.com/doc/refman/5.7/en/subquery-optimization.html),我们摘录如下:
对于如下的子查询,
被优化为:outer_expr
IN (SELECTinner_expr
FROM ... WHEREsubquery_where
)
EXISTS (SELECT 1 FROM ... WHEREsubquery_where
AND (outer_expr
=inner_expr
ORinner_expr
IS NULL))
这就是所谓的“EXISTS
strategy”。
至于为什么被优化为如上的形式,可以参阅:http://dev.mysql.com/doc/refman/5.7/en/subquery-optimization.html
的“Optimizing Subqueries with EXISTS Strategy”节内容。