比如一张表中的两列(id和c_id)都单独建立了索引,但是下面这种情况不会走索引
select * from table where id = c_id; //这种情况会被认为还不如走全表扫描
2、存在NULL值
我们在设计数据库时尽量避免NULL值的出现,如果不可避免地要出现NULL值的情况,也要这是默认值,比如数值类型的可以设置为0或者-1,字符串可以设成空字符串或者其他的东西。
如果索引列是可空的,是不会给其创建索引的,索引值是小于表的count(*)值的,这种情况下也会去全表扫描。
select * from table where id is not null;
3、存在NOT条件
我们知道建立索引的时候。给每一个索引建立一个条目,如果查询条件为等值查询或者范围查询的时候 ,索引可以根据查询条件去找对应的条目。但是如果查村条件为非得时候,索引就定位困难了,执行计划可能更倾向于全表扫描,这类查询条件有:<>、not 、not in 、not exit
select * from test where id<>500;
select * from test where id in (1,2,3,4,5); //不走索引
select * from test where id in (1); //走索引
select * from test where not in (6,7,8,9,0);
select * from test where not exists (select 1 from test_02 where test_02.id=test.id);
4、Like通配符
当使用模糊查询的时候尽量使用后置通配符,例如name || '%',前置匹配更倾向于全表扫描,而后置匹配可以走INDEX RANGE SCAN。
select * from table where name like 张|| '%'
5、条件中有or,索引也会失效
6、条件上包括函数
查询条件上尽量不要对有索引的列使用函数,例如:
select * from table where upper(name) == "ABC";
因为索引建立的时候会和计算以后的可能不同,无法定位到索引。但是如果查询条件不对索引列进行计算,那么依然可以走索引。例如:
select * from table where name = upper("abc"); ---INDEX RANGE SCAN