1、查询谓词没有使用索引的主要边界,换句话说就是select *,可能会导致不走索引。
比如,你查询的是SELECT * FROM T WHERE Y=XXX;假如你的T表上有一个包含Y值的组合索引,但是优化器会认为需要一行行的扫描会更有效,这个时候,优化器可能会选择TABLE ACCESS FULL,但是如果换成了SELECT Y FROM T WHERE Y = XXX,优化器会直接去索引中找到Y的值,因为从B树中就可以找到相应的值。
 
2、单键值的b树索引列上存在null值,导致COUNT(*)不能走索引。
如果在B树索引中有一个空值,那么查询诸如SELECT COUNT(*) FROM T 的时候,因为HASHSET中不能存储空值的,所以优化器不会走索引,有两种方式可以让索引有效,一种是SELECT COUNT(*) FROM T WHERE XXX IS NOT NULL或者把这个列的属性改为not null (不能为空)。
 
3、索引列上有函数运算,导致不走索引
如果在T表上有一个索引Y,但是你的查询语句是这样子SELECT * FROM T WHERE FUN(Y) = XXX。这个时候索引也不会被用到,因为你要查询的列中所有的行都需要被计算一遍,因此,如果要让这种sql语句的效率提高的话,在这个表上建立一个基于函数的索引,比如CREATE INDEX IDX FUNT ON T(FUN(Y));这种方式,等于Oracle会建立一个存储所有函数计算结果的值,再进行查询的时候就不需要进行计算了,因为很多函数存在不同返回值,因此必须标明这个函数是有固定返回值的。
 
4、隐式转换导致不走索引。
索引不适用于隐式转换的情况,比如你的SELECT * FROM T WHERE Y = 5 在Y上面有一个索引,但是Y列是VARCHAR2的,那么Oracle会将上面的5进行一个隐式的转换,SELECT * FROM T WHERE TO_NUMBER(Y) = 5,这个时候也是有可能用不到索引的。
 
5、表的数据库小或者需要选择大部分数据,不走索引
在Oracle的初始化参数中,有一个参数是一次读取的数据块的数目,比如你的表只有几个数据块大小,而且可以被Oracle一次性抓取,那么就没有使用索引的必要了,因为抓取索引还需要去根据rowid从数据块中获取相应的元素值,因此在表特别小的情况下,索引没有用到是情理当中的事情。
6、cbo优化器下统计信息不准确,导致不走索引
很长时间没有做表分析,或者重新收集表状态信息了,在数据字典中,表的统计信息是不准确的,这个情况下,可能会使用错误的索引,这个效率可能也是比较低的。
7、!=或者<>(不等于),可能导致不走索引,也可能走 INDEX FAST FULL SCAN
例如select id  from test where id<>100
8、表字段的属性导致不走索引,字符型的索引列会导致优化器认为需要扫描索引大部分数据且聚簇因子很大,最终导致弃用索引扫描而改用全表扫描方式,
由于字符型和数值型的在insert的时候排序不同,字符类型导致了聚簇因子很大,原因是插入顺序与排序顺序不同。详细点说,就是按照数字类型插入(1..3200000),按字符类型('1'...'32000000')t排序,在对字符类型使用大于运算符时,会导致优化器认为需要扫描索引大部分数据且聚簇因子很大,最终导致弃用索引扫描而改用全表扫描方式。
下面展示测试结果,
两个表的数据类型相似(只是ID字段类型不同),各插入了320万数据,ID字段范围为1~3200000。
模拟场景
相关代码如下:
对于普通的采用数值类型的字段,范围查询就是正常的索引范围扫描,执行效率很高。
对于文本类型字段的表,范围查询就是对应的全表扫描,效率较低是显而易见的。
解决方法
将SQL语句由开放区间扫描(>=),修改为封闭区间(between xxx and max_value)。使得数据在索引局部顺序是“对的”。如果采用这种方式仍然不走索引扫描,还可以进一步细化分段或者采用“逐条提取+批绑定”的方法。
 
9.建立组合索引,但查询谓词并未使用组合索引的第一列,此处有一个INDEX SKIP SCAN概念,
10、like '%liu' 百分号在前
11,not in ,not exist
可以尝试把not in 或者 not exsts改成左连接的方式(前提是有子查询,并且子查询有where条件)。
例如:
SELECT
    /*+ INDEX(I CIRCLEICONMAST_IX1)*/
    I.ICONNO,
    I.CIRCLEID,
    I.FILEPATH,
    I.REGDT,
    I.FILEPATH || '/' || I.FILENAME IMGNAME,
    I.FILEPATH || '/' || 'th_160_' || I.FILENAME SMALLIMGNAME,
    I.MEMBERID,
    I.ADMCHK STATUS,
    I.ADMCHK ORIGINALSTATUS,
    ROWNUM RN
     FROM CIRCLEICONMAST I
    WHERE I.REGDT BETWEEN TO_DATE('20120619', 'YYYYMMDD') - 10000 AND
      TO_DATE('20120621', 'YYYYMMDD')
      AND NOT EXISTS (
       SELECT C.VALIDFLG
         FROM CIRCLEMAST C
        WHERE C.VALIDFLG IN ('N', 'F')
        AND I.CIRCLEID = C.CIRCLEID)      
      AND I.ADMCHK = 'N'
 
改成左连接:
SELECT
/*+ INDEX(I CIRCLEICONMAST_IX1)*/
I.ICONNO,
I.CIRCLEID,
I.FILEPATH,
I.REGDT,
I.FILEPATH || '/' || I.FILENAME IMGNAME,
I.FILEPATH || '/' || 'th_160_' || I.FILENAME SMALLIMGNAME,
I.MEMBERID,
I.ADMCHK STATUS,
I.ADMCHK ORIGINALSTATUS,
ROWNUM RN
  FROM CIRCLEICONMAST I, CIRCLEMAST C
WHERE I.REGDT BETWEEN TO_DATE('20110620', 'YYYYMMDD') AND
       TO_DATE('20120621', 'YYYYMMDD') + 1
   AND C.VALIDFLG NOT IN ('N', 'F')
   AND I.CIRCLEID = C.CIRCLEID
      
   AND I.ADMCHK = 'N'
总结:oracle中有很多情况会导致index失效,并且走全表扫描的代价是相当大的,所以在写sql的时候一定要注意这个会使索引失效的情况,养成良好的习惯。

sql中索引不会被用到的几种情况的更多相关文章

  1. vue中下载excel的使用,后端链接两种情况,一个是链接,一个是文件流

    vue中下载excel使用 一.这是第一种情况,后台链接地址返回的是一个url,这个时候我只要在导出按钮上绑定exportData()这个事件方法就好了 exportData() {     this ...

  2. SQL中索引的原理

    (一)深入浅出理解索引结构         实际上,您可以把索引理解为一种特殊的目录.微软的SQL   SERVER提供了两种索引:聚集索引(clustered   index,也称聚类索引.簇集索引 ...

  3. Swift中方法闭包参数不能省略括号的一种情况

    大熊猫猪·侯佩原创或翻译作品.欢迎转载,转载请注明出处. 如果觉得写的不好请多提意见,如果觉得不错请多多支持点赞.谢谢! hopy ;) 我们知道在swift中,如果方法的最后一个参数是一个闭包类型, ...

  4. JQuery中根据属性或属性值获得元素(6种情况获取方法)

    根据属性获得元素 1.比如要获取页面p标签中属性有id的元素 $("p[id]").css("color","red"); 根据属性值获得元 ...

  5. java中的泛型和sql中的索引

    sql中的索引 索引:好处查询的速度快,被删除,修改,不会对表产生影响,作用是加速查询: 一种典型的数据库对象 作用:提交数据的查询效率,尤其对一些数据量很大的表 索引是用来为表服务的 索引是orac ...

  6. 理解SQL Server中索引的概念

    T-SQL查询进阶--理解SQL Server中索引的概念,原理以及其他   简介 在SQL Server中,索引是一种增强式的存在,这意味着,即使没有索引,SQL Server仍然可以实现应有的功能 ...

  7. [转帖]SQL Server 索引中include的魅力(具有包含性列的索引)

    SQL Server 索引中include的魅力(具有包含性列的索引) http://www.cnblogs.com/gaizai/archive/2010/01/11/1644358.html 上个 ...

  8. T-SQL查询进阶--理解SQL Server中索引的概念,原理以及其他

    简介 在SQL Server中,索引是一种增强式的存在,这意味着,即使没有索引,SQL Server仍然可以实现应有的功能.但索引可以在大多数情况下大大提升查询性能,在OLAP中尤其明显.要完全理解索 ...

  9. 理解SQL Server中索引的概念,原理

    转自:http://www.cnblogs.com/CareySon/archive/2011/12/22/2297568.html 简介 在SQL Server中,索引是一种增强式的存在,这意味着, ...

随机推荐

  1. poj 1511 正向 反向 构两个图

    有向图 源点为1 求源点到其他各点的最短距离之和 再在其他点到源点的最短距离之和 再加起来 多源点一终点 只要反向构图就行了 Sample Input 2 //T2 2 //结点数 边数1 2 13 ...

  2. [HNOI2010]CITY 城市建设

    问题: 给一张图,支持边长度修改,求MST 题解: 自己想就想不到了.. 考虑cdq分治 1.首先求出一定有用的边 对于未处理的边,全部设为-INF,求一次MST,出现在MST上的边一定最终出现在后面 ...

  3. openstack学习-Horizon安装(八)

    一.安装Horizon [root@linux-node2 ~]# yum install -y openstack-dashboard 二.Horizon配置 [root@linux-node2 ~ ...

  4. word 中如何取消格式标记

    开始菜单栏下: 或者:

  5. 《Gradle权威指南》--Gradle任务

    No1: 多种方式创建任务 def Task ex41CreateTask1 = task(ex41CreateTask1) ex41CreateTask1.doLast{ println " ...

  6. canvas三角函数模拟水波效果

    .katex { display: block; text-align: center; white-space: nowrap; } .katex-display > .katex > ...

  7. 简述synchronized和java.util.concurrent.locks.Lock的异同?

    主要相同点:Lock能完成synchronized所实现的所有功能 . 主要不同点:Lock有比synchronized更精确的线程语义和更好的性能.synchronized会自动释放锁,而Lock一 ...

  8. BZOJ 4405 [wc2016]挑战NPC 带花树 一般图最大匹配

    https://www.lydsy.com/JudgeOnline/problem.php?id=4405 这道题大概就是考场上想不出来,想出来也调不出来的题. 把每个桶拆成三个互相有边的点,每个球向 ...

  9. Python3面向对象基础

    面向对象概述 面向对象 面向对象的世界,引入了对象的概念,对象具有属性:数据,对象具有过程或者方法:成员函数.成员函数的作用就是处理属性. 例子 对象:Car 属性:fuel_level, isSed ...

  10. Redis淘汰删除策略

    Redis淘汰删除策略 Redis淘汰删除策略6种淘汰Key策略3种删除过期键策略定时删除惰性删除定期删除其他模块的淘汰处理RDB 快照持久化创建载入AOF 只追加持久化写入重写主从复模式下对过期键的 ...