ICP(Index Condition Pushdown)索引下推

什么是索引下推了?

MySQL的“索引下推”(Index Condition Pushdown,简称ICP)是MySQL 5.6引入的一个优化特性。这个特性允许MySQL在执行索引查询时,将某些条件判断下推到索引扫描阶段,从而减少需要检查的行数,提高查询效率。

传统的MySQL查询执行流程如下:

  1. 从索引中检索行。
  2. 将行从索引载入到内存。
  3. 在内存中对行应用WHERE子句中的条件。
  4. 返回满足条件的行。

5.6之后

如果WHERE子句中的某些条件可以基于索引值进行判断,那么这些条件就可以在从索引检索行时被评估,而不是等到行被加载到内存后再评估。这样可以减少需要检查的行数,提高查询效率。这个过程减少了需要从磁盘读取的数据量,因为只有满足条件的行才会被加载到内存中。这可以提高查询性能,特别是在大数据集上。

需要注意的是,不是所有的WHERE子句条件都可以被下推到索引扫描阶段。只有那些可以在索引扫描阶段被评估的条件才会被下推。

举个例子:

对于辅助的联合索引(name,age,position),正常情况按照最左前缀原则,SELECT * FROM employees WHERE name like 'LiLei%' AND age = 22 AND position ='manager' 这种情况只会走name字段索引,因为根据name字段过滤完,得到的索引行里的age和position是无序的,无法很好的利用索引。

在MySQL5.6之前的版本,这个查询只能在联合索引里匹配到名字是 'LiLei' 开头的索引,然后拿这些索引对应的主键逐个回表,到主键索引上找出相应的记录,再比对age和position这两个字段的值是否符合。

MySQL 5.6引入了索引下推优化,可以在索引遍历过程中,对索引中包含的所有字段先做判断,过滤掉不符合条件的记录之后再回表,可以有效的减少回表次数。使用了索引下推优化后,上面那个查询在联合索引里匹配到名字是 'LiLei' 开头的索引之后,同时还会在索引里过滤age和position这两个字段,拿着过滤完剩下的索引对应的主键id再回表查整行数据。

索引下推会减少回表次数,对于innodb引擎的表索引下推只能用于二级索引,innodb的主键索引(聚簇索引)树叶子节点上保存的是全行数据,所以这个时候索引下推并不会起到减少查询全行数据的效果。

为什么范围查找Mysql没有用索引下推优化?

在MySQL中,LIKE 查询和 BETWEEN 范围查询都可以利用索引下推(ICP)来提高查询性能。但是,是否使用索引下推取决于多种因素,包括查询的具体条件、索引类型、表统计信息和优化器的决策等。

  1. LIKE 查询:

    • 当使用 LIKE 查询时,如果模式匹配从模式开始 (%pattern),索引下推可能会非常有用。例如,对于 LIKE 'a%',MySQL可能会使用索引下推来快速定位以 'a' 开头的行。
    • 如果模式匹配从模式末尾开始 (pattern%),则索引下推可能不会起作用,因为MySQL需要扫描整个索引来查找匹配的行。
  2. BETWEEN 范围查询:

    • 对于 BETWEEN 范围查询,如果查询条件适用于索引的连续范围,并且有足够的索引选择性(即不同的索引值对应的行数差异较大),则MySQL可能会使用索引下推来加速查询。
    • 如果范围查询条件跨越了索引的多个不连续部分,或者范围查询条件的选择性不高,那么索引下推可能不会带来太大的性能提升。

总之,是否使用索引下推取决于多种因素,包括查询的具体条件、索引类型、表统计信息和优化器的决策等。为了获得最佳性能,建议定期分析和优化数据库查询,并确保索引被适当地使用和优化。

你可能感兴趣的:(mysql,数据库,mysql,ICP,索引下推)