我们进行SQL优化时,经常会碰到对大量数据集进行排序,然后从排序后的集合取前部分结果的需求,这种情况下,当我们按照常规思路去写SQL时,系统会先读取过滤获得所有集合,然后进行排序,再从排序结果取出极少量结果,这个过程中,大量数据的扫描读取、过滤、排序会消耗掉大量的系统资源,SQL性能也会存在很大的问题,实践中,几分钟乃至几个小时不出结果的情况很常见。为了优化这种场景的SQL,我们经常会让查询顺序扫描建在排序列上的索引,已避开大量的数据读取和排序。

但实践中发现,当索引列不在条件中出现时,ORACLE不会产生扫描索引的计划,即使用hint也不能让查询沿着目的索引扫描,例如:

create table t1(c1 int,c2 char(10));

create index idx1_t1 on t1(c1);

select * from (

select  * from t1 order by c1)

where rownum<6;

很明显,这种写法会导致先读取表,再进行排序,然后取前5条记录,计划如下:

如果我们这么写,语义是一样的,但会省去了大量的读取和排序代价:

select /*+ index(t1,idx1_t1)*/* from t1 where rownum<6;

该SQL的执行计划如下:

大家可以看到,该SQL并没按照hint指示,顺序扫描idx1_t1索引,这是为什么呢?个人猜测,可能是Oracle优化器认为过滤条件内没c1列,走索引比走FTS效率更低,所以,干脆就不考虑走索引这种计划,即使用hint也要忽略,这点感觉有点不尽人意。那么,我们想什么办法才能让优化器选择扫描idx1_t1的计划呢?我们只需要在where中加个c1列上的条件就可以了,例如:

select /*+ index(t1,idx1_t1)*/* from t1 where rownum<6 and c1<>-1;

这么修改后的计划如下:

由此可见,我们优化类似场景时,只需满足两点:

1、排序列上存在索引;

2、where条件中有该索引列上的条件;

如果能实现按照索引扫描,性能有成千上万倍的提升也是非常可能的,这点在实践中得到了验证。

SQL优化(SQL TUNING)可大幅提升性能的实战技巧之一——让计划沿着索引跑的更多相关文章

  1. Java 性能优化手册 — 提高 Java 代码性能的各种技巧

    转载: Java 性能优化手册 - 提高 Java 代码性能的各种技巧 Java 6,7,8 中的 String.intern - 字符串池 这篇文章将要讨论 Java 6 中是如何实现 String ...

  2. oracle 11g亿级复杂SQL优化一例(数量级性能提升)

    自从16年之后,因为工作原因,项目中就没有再使用oracle了,最近最近支持一个项目,又要开始负责这块事情了.最近在跑性能测试,配置全部调好之后,不少sql还存在性能低下的问题,主要涉及执行计划的不合 ...

  3. 面试题: 数据库 sql优化 sql练习题 有用 学生表,课程表,成绩表,教师表 练习

    什么是存储过程?有哪些优缺点? 什么是存储过程?有哪些优缺点? 存储过程就像我们编程语言中的函数一样,封装了我们的代码(PLSQL.T-SQL). 存储过程的优点: 能够将代码封装起来 保存在数据库之 ...

  4. SQL优化SQL tuning

    1. 索引不合适,走主键进行了key lookup查找   说明索引没有覆盖到where条件 或者  orderby 或者 group by的列

  5. sql 优化 -- sql中的自定函数

    Long run sql: MERGE INTO INTITMRTNPARAM D USING ( SELECT A.INRFILENM,A.INRSTAT,A.INRDEPCD,A.INRITMCD ...

  6. SQL优化 | sql执行过长的时间,如何优化?

    1.查看sql是否涉及多表的联表或者子查询,如果有,看是否能进行业务拆分,相关字段冗余或者合并成临时表(业务和算法的优化) 2.涉及链表的查询,是否能进行分表查询,单表查询之后的结果进行字段整合 3. ...

  7. SQL 优化SQL查询

    摘至于:http://www.cnblogs.com/ATree/archive/2011/02/13/sql_optimize_1.html 1. 首先要搞明白什么叫执行计划? 执行计划是数据库根据 ...

  8. SQL优化笔记一:索引和explain

    目录 为什么需要优化SQL SQL优化的重点 索引 索引的结构 索引的优缺点总结: 索引的分类 索引操作 B树 实战 问题 数据库方面,我会使用MySQL来讲解 为什么需要优化SQL 性能低,执行时间 ...

  9. php面试专题---Mysql索引原理及SQL优化

    php面试专题---Mysql索引原理及SQL优化 一.总结 一句话总结: 注意:只写精品 1.为表设置索引要付出代价 是什么? 存储空间:一是增加了数据库的存储空间 修改插入变动索引时间:二是在插入 ...

随机推荐

  1. ELK学习笔记之Elasticsearch启动常见错误

    问题出现的环境: OS版本:CentOS-7-x86_64-Minimal-1708 ES版本:elasticsearch-6.2.2 1. max file descriptors [4096] f ...

  2. VM三种网络连接方式

    bridge:这种方式最简单,直接将虚拟网卡桥接到一个物理网卡上面,和Linux下一个网卡 绑定两个不同地址类似,实际上是将网卡设置为混杂模式,从而达到侦听多个IP的能力. 在此种模式下,虚拟机内部的 ...

  3. Python的递归

    递归 是指函数/过程/子程序在运行过程序中直接或间接调用自身而产生的重入现象.在计算机编程里,递归指的是一个过程:函数不断引用自身,直到引用的对象已知.使用递归解决问题,思路清晰,代码少.但是在主流高 ...

  4. 终于在nowcoder爆发了的懒惰

    题目 这类题目我实在忍不了了 Emma,随便做个nowcode比赛题吧,我在oj上也没找到 题意 求\(\sum_{L=1}^{n}\sum_{R=i}^{n}a[k](L<=k<=R)\ ...

  5. BZOJ2724 [Violet]蒲公英 分块

    题目描述 经典区间众数题目 然而是权限题,所以题目链接放Luogu的 题解 因为太菜所以只会$O(n*\sqrt{n}+n*\sqrt{n}*log(n))$的做法 就是那种要用二分的,并不会clj那 ...

  6. [SpringBoot] - 一份笔记

    一. Spring Boot 入门 1. Spring Boot 简介 简化Spring应用开发的一个框架; 整个Spring技术栈的一个大整合; J2EE开发的一站式解决方案; 2. 微服务 201 ...

  7. C#学习笔记(八):多维数组

    一维数组 冒泡排序 二维数组 Length:取数组元素的总个数 GetLength:取不同维度的个数 using System; using System.Collections.Generic; u ...

  8. Spring资源加载基础ClassLoader

    1 ClassLoader工作机制 1.1 ClassLoader作用 寻找类字节码文件并构造出类在JVM内部表示的组件.负责运行时查找和装入Class字节码文件 1.2 装载步骤 1.2.1 装载 ...

  9. java 编程技巧

    1. 参数可空: @注解表示修改的字段可为空值.看它的定义,可以修饰在方法,参数和字段(类似c#中的?)上. @Target({ElementType.METHOD, ElementType.PARA ...

  10. HTTP协议中TCP的三次握手 and HTTPS

    https://www.cnblogs.com/zxh930508/p/5432700.html https://www.cnblogs.com/digdeep/p/4832885.html