# ICP
ICP(Index Condition Pushdown) 索引条件下推
MySQL 5.6开始支持ICP(Index Condition Pushdown),用于优化数据查询。
- 不支持
ICP之前,当进行索引查询时,首先根据索引来查找数据,然后再根据where条件来过滤,扫描了大量不必要的数据,增加了数据库IO操作。 - 在支持
ICP后,MySQL在取出索引数据的同时,判断是否可以进行where条件过滤,将where的部分过滤操作放在存储引擎层,提前过滤掉不必要的数据,减少了不必要数据被扫描带来的IO开销。
索引条件下推的关键操作就是将与非主键索引上相关的条件由Server层向下传递至存储引擎层,由此减少回表IO次数,大大提升了查询的效率。
# ICP 特性
- 支持
range,ref,eq_ref,ref_or_null,并且需要回表查询的非聚集索引 - 支持
InnoDB、MyISAM的普通表及分区表 - 对于
InnoDB表,仅支持走非聚集索引的查询 Explain中Extra = "Using index condition; "
所以它不支持以下几点
- 不支持
主键索引 - 不支持基于虚拟列的
辅助索引 - 不支持
where条件涉及子查询的 - 不支持
where条件包含存储过程、函数的
# EXPLAIN 分析

Extra显示的索引扫描方式如下:
using where:查询使用索引的情况下,需要回表去查询所需的数据。using index condition:查询使用了索引,但是需要回表查询数据。using index:查询使用覆盖索引的时候会出现。using index & using where:查询使用了索引,但是需要的数据都在索引列中能找到,不需要回表查询数据。
# ICP 相关控制参数
index_condition_pushdown:索引条件下推默认开启的,可以设置为off关闭ICP特性。
mysql>show variables like 'optimizer_switch';
# 开启或者关闭ICP特性
mysql>set optimizer_switch = 'index_condition_pushdown=on | off';
1
2
3
4
2
3
4