Oracle SQL优化
1、书写顺序和执行顺序
在Oracle SQL中,查询的书写顺序和执行顺序是不同的。
1.1SQL书写顺序如下:
- SELECT
- FROM
- WHERE
- GROUP BY
- HAVING
- ORDER BY
1.2 SQL执行顺序
FROM:数据源被确定,表连接操作也在此步骤完成。
- WHERE:对数据行进行筛选。
- GROUP BY:将数据划分为不同的组。
- HAVING:筛选满足条件的分组。
- SELECT:选择具体的列,此时可以处理聚合函数或者别名等。
- ORDER BY:最后对结果集进行排序。
注意,虽然SELECT在书写顺序中处于第一位,但在执行顺序中却是倒数第二个,因为只有在前面的步骤都完成之后,才能知道要返回哪些列。
1.3 Oracle数据库执行SQL语句的步骤
Oracle数据库执行SQL语句的步骤主要包括以下几个阶段:
-
解析(Parse):在这一阶段,Oracle会检查SQL语句的语法和语义是否正确,并生成相应的解析树。同时,Oracle还会检查用户是否有执行该SQL语句的权限。
-
绑定(Bind):如果SQL语句中包含了绑定变量(即参数化查询中的参数),则这些变量在此阶段被赋值。
-
优化(Optimize):在这一阶段,优化器将选择一个或多个执行计划。执行计划定义了如何读取和处理数据的顺序和方式。优化器将基于统计信息和其他因素来决定最优的执行计划。
-
行源生成(Row Source Generation):生成用于从底层数据结构获取数据的可执行代码。
-
执行(Execute):根据优化器生成的执行计划,实际执行SQL语句。如果是查询语句,则返回结果集;如果是插入、更新或删除语句,则修改数据并返回影响的行数。
-
获取(Fetch):对于查询操作,它包括检索并返回结果集中的行。
其中,解析、优化和行源生成三个阶段通常被合称为“编译”,而执行和获取两个阶段通常被合称为“运行”。
注意,这个过程可以通过数据库中的一些机制(如语句缓存、绑定变量等)来进行优化,以减少编译时间并提高查询执行的效率。
2、 优化Oracle数据库查询SQL
优化Oracle数据库查询SQL主要是为了提高查询的性能和效率。以下是一些常用的优化技巧:
2.1 使用索引
如果经常需要查询某个特定的列,应该为这个列创建索引。但请注意,不应该为数据库中的每一列都创建索引,因为索引会占用额外的存储空间,并且每次数据变更时,都需要更新索引。
例如,如果你经常执行诸如:
ELECT * FROM employees WHERE employee_id = 123;
那么在employee_id上创建一个索引就很有用。但请记住,索引虽然可以加速数据查询,却会减慢数据插入、更新和删除的速度,因为每次数据变动,都要维护索引。
2.2 避免全表扫描
尽量通过WHERE子句筛选出所需要的记录,而不是读取整个表的数据。
比如使用
SELECT name, age FROM employees;
而不是
SELECT * FROM employees;
这样可以避免读取不必要的数据,提升查询速度。
2.3 减少连接操作
如果可能,试图减少连接多个表的操作。因为连接操作通常需要消耗比较大的资源。
当进行多表联接时,尝试减少JOIN操作的数量,确保ON子句中连接字段已被正确索引。此外,尽量避免在大表之间进行笛卡尔积(无约束条件的JOIN)。
2.4 使用EXPLAIN PLAN
Oracle 提供了EXPLAIN PLAN语句,它可以显示Oracle如何执行SQL查询。你可以根据EXPLAIN PLAN的结果来调整你的查询。
通过运行
EXPLAIN PLAN FOR your_sql_statement;
然后查询PLAN_TABLE表或使用DBMS_XPLAN.DISPLAY;
来查看计划,找出是否存在全表扫描、使用了哪些索引等信息。
2.4.1 执行计划的常用列字段解释:
基数(Rows):Oracle估计的当前操作的返回结果集行数
字节(Bytes):执行该步骤后返回的字节数
耗费(COST)、CPU耗费:Oracle估计的该步骤的执行成本,用于说明SQL执行的代价, 理论上越小越好(该值可能与实际有出入)
时间(Time):Oracle估计的当前操作所需的时间
2.4.2.执行顺序:
根据Operation缩进来判断,缩进最多的最先执行;(缩进相同时,最上面的最先执行)
2.4.3 检索方式:
1.TABLE ACCESS BY … 即描述的是该动作执行时表访问(或者说Oracle访问数据)的方式(非全部):
a.TABLE ACCESS FULL(全表扫描):
- Oracle会读取表中所有的行,并检查每一行是否满足SQL语句中的 Where 限制条件;
- 全表扫描时可以使用多块读(即一次I/O读取多块数据块)操作,提升吞吐量;
- 使用建议:数据量太大的表不建议使用全表扫描,除非本身需要取出的数据较多,占到表数据总量的 5% ~ 10% 或以上
b.ABLE ACCESS BY ROWID(通过ROWID的表存取):
- ROWID是由Oracle自动加在表中每行最后的一列伪列,既然是伪列,就说明表中并不会物理存储ROWID的值;
- 你可以像使用其它列一样使用它,只是不能对该列的值进行增、删、改操作;
- 一旦一行数据插入后,则其对应的ROWID在该行的生命周期内是唯一的,即使发生行迁移,该行的ROWID值也不变。
- 让我们再回到 TABLE ACCESS BY ROWID 来:行的ROWID指出了该行所在的数据文件、数据块以及行在该块中的位置,所以通过ROWID可以快速定位到目标数据上,这也是Oracle中存取单行数据最快的方法;
c.TABLE ACCESS BY INDEX SCAN(索引扫描):
-
在索引块中,既存储每个索引的键值,也存储具有该键值的行的ROWID。
-
所以索引扫描其实分为两步:
-
Ⅰ:扫描索引得到对应的ROWID
-
Ⅱ:通过ROWID定位到具体的行读取数据
-
d.TABLE ACCESS BY INDEX ROWID BATCHED:
The BATCHED access shown in Step 1 means that the database retrieves a few rowids from the index, and then attempts to access rows in block order to improve the clustering and reduce the number of times that the database must access a block.
- 这句话的意思是说,该操作是数据库为了从索引中获取一些rowid,接着,试着按照块顺序存取块中的数据行,以便用来改善聚集效果和减少对一个数据块存取的次数。
- 官方解释的意思就是这样,但怎么理解呢?之前,当我们通过索引获取的rowid回表获取相应数据行时,都是读一个rowid回表获取一次相应数据行,然后,再读一个rowid,再回表获取一次相应数据行。
- 这样一直读取完所有所需数据。当不同rowid对应的数据行存储在一个数据块中时,就可能会发生对同一表数据块的多次读取,当一个索引的聚集因子比较低时,这也是一个必然结果,从而浪费了系统资源。Oracle 12c中该新特性,通过对rowid对应的数据块号进行排序,然后回表读取相应数据行,从而避免了对同一表数据块的多次重复读取,从而改善了SQL语句的性能,降低了资源消耗。该特性通过隐藏参数“_optimizer_batch_table_access_by_rowid”控制,默认值为true,即为开启。
2.4.4 索引扫描延伸
索引扫描又分五种:
(a)INDEX UNIQUE SCAN(索引唯一扫描)
-
针对唯一性索引(UNIQUE INDEX)的扫描,每次至多只返回一条记录;
-
表中某字段存在 UNIQUE、PRIMARY KEY 约束时,Oracle常实现唯一性扫描;
(b)INDEX RANGE SCAN(索引范围扫描)
- 使用一个索引存取多行数据;
- 发生索引范围扫描的三种情况:
- 在唯一索引列(unique索引)上使用了范围操作符(如:> < <> >= <= between)
- 在组合索引上,只使用部分列进行查询(查询时必须包含前导列,否则会走全表扫描)对非唯一索引列(非unique)上进行的任何查询
(c)INDEX FULL SCAN(索引全扫描)
- 进行全索引扫描时,查询出的数据都必须从索引中可以直接得到(注意全索引扫描只有在CBO模式下才有效)
(d)INDEX FAST FULL SCAN(索引快速扫描)
- 扫描索引中的所有的数据块,与 INDEX FULL SCAN 类似,但是一个显著的区别是它不对查询出的数据进行排序(即数据不是以排序顺序被返回)
(e)INDEX SKIP SCAN(索引跳跃扫描)
- Oracle 9i后提供,有时候复合索引的前导列(索引包含的第一列)没有在查询语句中出现,oralce也会使用该复合索引,这时候就使用的INDEX SKIP SCAN;什么时候会触发INDEX SKIP SCAN 呢?
- 前提条件:表有一个复合索引,且在查询时有除了前导列(索引中第一列)外的其他列作为条件,并且优化器模式为CBO时当Oracle发现前导列的唯一值个数很少时,会将每个唯 一值都作为常规扫描的入口,在此基础上做一次查找,最后合并这些查询;
- 例如:假设表emp有ename(雇员名称)、job(职位名)、sex(性别)三个字段,并且建立了如 create index idx_emp on emp (sex, ename, job) 的复合索引;因为性别只有 '男' 和 '女' 两个值,所以为了提高索引的利用率,Oracle可将这个复合索引拆成 ('男', ename, job),('女', ename, job) 这两个复合索引;当查询 select * from emp where job = 'Programmer' 时,该查询发出后:Oracle先进入sex为'男'的入口,这时候使用到了 ('男', ename, job) 这条复合索引,查找 job = 'Programmer' 的条目;再进入sex为'女'的入口,这时候使用到了('女', ename, job) 这条复合索引,查找 job = 'Programmer' 的条目;最后合并查询到的来自两个入口的结果集。
----------------分区表扫描方式-----------------------
PARTITION RANGE ALL 扫描所有分区
PARTITION RANGE ITERATOR 扫描部分分区
PARTITION RANGE SINGLE 扫描单个分区
2.5 合理使用子查询和连接
在某些情况下,子查询可能比连接操作更高效,或者反过来。你需要根据具体情况来选择使用哪种方式。
当进行多表联接时,尝试减少JOIN操作的数量,确保ON子句中连接字段已被正确索引。此外,尽量避免在大表之间进行笛卡尔积(无约束条件的JOIN)。
2.6 使用分区
对于非常大的表,你可以考虑使用分区。分区可以将一个大表分割成多个较小的部分,从而提高查询性能。
2.7 调整数据库参数
Oracle 允许你调整很多数据库参数,根据工作负载和硬件的特性,调整Oracle的初始化参数,例如缓存大小、I/O配置等,也可以提高查询性能。
2.8 避免频繁提交
每次提交都会生成redo日志,消耗I/O资源。如果事务较小,尝试降低提交的频率。
相关文章:

Oracle SQL优化
1、书写顺序和执行顺序 在Oracle SQL中,查询的书写顺序和执行顺序是不同的。 1.1SQL书写顺序如下: SELECTFROMWHEREGROUP BYHAVINGORDER BY 1.2 SQL执行顺序 FROM:数据源被确定,表连接操作也在此步骤完成。 WHERE:对…...

C++实现ATM取款机
C实现ATM取款机 代码:https://mbd.pub/o/bread/ZZeZk5Zp 1.任务描述 要求:设计一个程序,当输入给定的卡号和密码(初始卡号和密码为123456) 时,系统 能登录 ATM 取款机系统,用户可以按照以下规则进行: 查询…...

【数电笔记】11-最小项(逻辑函数的表示方法及其转换)
目录 说明: 逻辑函数的建立 1. 分析逻辑问题,建立逻辑函数的真值表 2. 根据真值表写出逻辑式 3. 画逻辑图 逻辑函数的表示 1. 逻辑表达式的常见表示形式与转换 2. 逻辑函数的标准表达式 (1)最小项的定义 (2&am…...

Gradio库的安装和使用教程
目录 一、Gradio库的安装 二、Gradio的使用 1、导入Gradio库 2、创建Gradio接口 3、添加接口到Gradio应用 4、处理用户输入和模型输出 5、关闭Gradio应用界面 三、Gradio的高级用法 1、多语言支持 2、自定义输入和输出格式 3、模型版本控制 4、集成第三方库和API …...

【BLE基础知识】--Slave latency设置流程及空中包解析
1、Slave latency基本概念 当BLE从设备对耗电量要求较高时,若需要节省耗电量,则可以通过设置Slave Latency参数来减少BLE从设备的耗电。 Slave Latency:允许Slave(从设备)在没有数据要发的情况下,跳过一定…...

数据结构之堆排序以及Top-k问题详细解析
个人主页:点我进入主页 专栏分类:C语言初阶 C语言程序设计————KTV C语言小游戏 C语言进阶 C语言刷题 数据结构初阶 欢迎大家点赞,评论,收藏。 一起努力 目录 1.前言 2.堆排序 2.1降序排序 2.2时间复杂…...

ESP32-Web-Server 实战编程-通过网页控制设备多个 GPIO
ESP32-Web-Server 实战编程-通过网页控制设备多个 GPIO 概述 上节 ESP32-Web-Server 实战编程-通过网页控制设备的 GPIO 讲述了如何通过网页控制一个 GPIO。本节实现在网页上控制多个 GPIO。 示例解析 前端设计 前端代码建立了四个 GPIO,如下死 GPIO 2 在前端的…...
说一说MySQL中的锁机制
说一说MySQL中的锁机制 按粒度大小从大到小分为 全局锁 全局锁 全局锁是对整个数据库的锁,最常用的全局锁就是读写锁 读锁 阻止其他用户更新数据,允许其他用户读数据写锁 阻止其他用户更新和读数据 修改一些大量的数据,并且不希望其他用户…...

C++笔试训练day_1
文章目录 选择题编程题 选择题 编程题 #include <iostream> #include <algorithm> #include <vector>using namespace std;int main() {int n 0;cin >> n;vector<int> v;v.resize(3 * n);int x 0;for(int i 0; i < v.size(); i){cin >&…...

详解Spring对Mybatis等持久化框架的整合
😉😉 学习交流群: ✅✅1:这是孙哥suns给大家的福利! ✨✨2:我们免费分享Netty、Dubbo、k8s、Mybatis、Spring...应用和源码级别的视频资料 🥭🥭3:QQ群:583783…...
[Electron] 将应用打包成供Ubuntu、Debian平台下安装的deb包
在使用 electron-packager 工具输出 linux 平台的 electron app 后,可以使用 electron-installer-debian 工具把 app 打包成供Ubuntu平台下安装的 debian 包。 electron-installer-debian是一个用于创建 Debian Linux(.deb)安装包的开发工…...

7.24 SpringBoot项目实战【审核评论】
文章目录 前言一、编写控制器二、编写服务层三、Postman测试前言 我们在 上文 7.23 已经实现了 评论 功能,本文我们继续SpringBoot项目实战 审核评论 功能。逻辑如下: 一是判断管理员权限,关于角色权限校验 在 7.5 和 7.6 分别基于 拦截器Interceptor 和 切面AOP 都实现过…...

Java实现动态加载的逻辑
日常工作中我们经常遇到这样的场景,某某些逻辑特别不稳定,随时根据线上实际情况做调整,比如商品里的评分逻辑,比如规则引擎里的规则。 常见的可选方案有: JDK自带的ScriptEngine 使用groovy,如GroovyClassLoader、Gro…...
数据库的设计规范
文章目录 第一范式(1NF):列不可再分 第二范式 (2NF):所有非主键字段,都必须 完全依赖主键,不能部分依赖 第三范式(3NF):所有非主键字段不能依赖于…...

正则表达式从放弃到入门(2):grep命令详解
正则表达式从放弃到入门(2):grep命令详解 总结 本博文转载自 这是一篇”正则表达式”扫盲贴,如果你还不理解什么是正则表达式,看这篇文章就对了。 如果你是一个新手,请从头阅读这篇文章,如果你…...

用Java写一个王者荣耀游戏
目录 sxt包 Background Bullet Champion ChampionDaji GameFrame GameObject Minion MinionBlue MinionRed Turret TurretBlue TurretRed beast包 Bear Beast Bird BlueBuff RedBuff Wolf Xiyi 打开Eclipse创建图片中的几个包 sxt包 Background package sxt;…...

基于SSM的新闻网站浏览管理实现与设计
基于ssm的新闻网站浏览管理实现与设计 摘要:在大数据时代下,科技与技术日渐发达的时代,人们不再局限于只获取自己身边的信息,而是对全球信息获取量也日渐提高,网络正是打开这新世纪大门的钥匙。在传统方式下ÿ…...

【蓝桥杯软件赛 零基础备赛20周】第6周——栈
文章目录 1. 基本数据结构概述1.1 数据结构和算法的关系1.2 线性数据结构概述1.3 二叉树简介 2. 栈2.1 手写栈2.2 CSTL栈2.3 Java 栈2.4 Python栈 3 习题 1. 基本数据结构概述 很多计算机教材提到:程序 数据结构 算法。 “以数据结构为弓,以算法为箭”…...
CWE/SANS TOP 25 2022
我整理了CWE/SANS TOP25 2022年的这25类缺陷,分类适合的开发语言,其实主要是C/C语言的缺陷相对于Java、PHP、Python、C#等更高级的语言的不同,所以分为适合C/C语言和其它语言。但是大家不要纠结,例如SQL难道C/C语言程序没有吗&…...

Qt 天气预报项目
参考引用 QT开发专题-天气预报 1. JSON 数据格式 1.1 什么是 JSON JSON (JavaScript Object Notation),中文名 JS 对象表示法,因为它和 JS 中对象的写法很类似 通常说的 JSON,其实就是 JSON 字符串,本质上是一种特殊格式的字符串…...

手游刚开服就被攻击怎么办?如何防御DDoS?
开服初期是手游最脆弱的阶段,极易成为DDoS攻击的目标。一旦遭遇攻击,可能导致服务器瘫痪、玩家流失,甚至造成巨大经济损失。本文为开发者提供一套简洁有效的应急与防御方案,帮助快速应对并构建长期防护体系。 一、遭遇攻击的紧急应…...

css实现圆环展示百分比,根据值动态展示所占比例
代码如下 <view class""><view class"circle-chart"><view v-if"!!num" class"pie-item" :style"{background: conic-gradient(var(--one-color) 0%,#E9E6F1 ${num}%),}"></view><view v-else …...
多模态商品数据接口:融合图像、语音与文字的下一代商品详情体验
一、多模态商品数据接口的技术架构 (一)多模态数据融合引擎 跨模态语义对齐 通过Transformer架构实现图像、语音、文字的语义关联。例如,当用户上传一张“蓝色连衣裙”的图片时,接口可自动提取图像中的颜色(RGB值&…...
五年级数学知识边界总结思考-下册
目录 一、背景二、过程1.观察物体小学五年级下册“观察物体”知识点详解:由来、作用与意义**一、知识点核心内容****二、知识点的由来:从生活实践到数学抽象****三、知识的作用:解决实际问题的工具****四、学习的意义:培养核心素养…...
sqlserver 根据指定字符 解析拼接字符串
DECLARE LotNo NVARCHAR(50)A,B,C DECLARE xml XML ( SELECT <x> REPLACE(LotNo, ,, </x><x>) </x> ) DECLARE ErrorCode NVARCHAR(50) -- 提取 XML 中的值 SELECT value x.value(., VARCHAR(MAX))…...
iOS性能调优实战:借助克魔(KeyMob)与常用工具深度洞察App瓶颈
在日常iOS开发过程中,性能问题往往是最令人头疼的一类Bug。尤其是在App上线前的压测阶段或是处理用户反馈的高发期,开发者往往需要面对卡顿、崩溃、能耗异常、日志混乱等一系列问题。这些问题表面上看似偶发,但背后往往隐藏着系统资源调度不当…...

安宝特案例丨Vuzix AR智能眼镜集成专业软件,助力卢森堡医院药房转型,赢得辉瑞创新奖
在Vuzix M400 AR智能眼镜的助力下,卢森堡罗伯特舒曼医院(the Robert Schuman Hospitals, HRS)凭借在无菌制剂生产流程中引入增强现实技术(AR)创新项目,荣获了2024年6月7日由卢森堡医院药剂师协会࿰…...
Mysql8 忘记密码重置,以及问题解决
1.使用免密登录 找到配置MySQL文件,我的文件路径是/etc/mysql/my.cnf,有的人的是/etc/mysql/mysql.cnf 在里最后加入 skip-grant-tables重启MySQL服务 service mysql restartShutting down MySQL… SUCCESS! Starting MySQL… SUCCESS! 重启成功 2.登…...
【Nginx】使用 Nginx+Lua 实现基于 IP 的访问频率限制
使用 NginxLua 实现基于 IP 的访问频率限制 在高并发场景下,限制某个 IP 的访问频率是非常重要的,可以有效防止恶意攻击或错误配置导致的服务宕机。以下是一个详细的实现方案,使用 Nginx 和 Lua 脚本结合 Redis 来实现基于 IP 的访问频率限制…...

FFmpeg:Windows系统小白安装及其使用
一、安装 1.访问官网 Download FFmpeg 2.点击版本目录 3.选择版本点击安装 注意这里选择的是【release buids】,注意左上角标题 例如我安装在目录 F:\FFmpeg 4.解压 5.添加环境变量 把你解压后的bin目录(即exe所在文件夹)加入系统变量…...