Oracle 多表查询实战技巧主要包括优化表连接顺序、合理使用索引、避免全表扫描及减少数据库访问次数。数据库优化新策略通过调整 FROM 子句表顺序(小表在后)、WHERE 子句条件顺序(过滤性强的在后)、使用 EXISTS 替代 IN、避免 SELECT * 以及利用绑定变量等方式,显著提升数据处理效率。此外,定期更新统计信息、使用执行计划分析工具及合理配置内存参数也是关键措施,能有效降低系统资源消耗,加快查询响应速度。
多表查怎么加复合索引 多表查询如何提高效率
(1) 选择最有效率的表名顺序 (只在基于规则的优化器中有效): ORACLE 的解析器按照从右到左的顺序处理 FROM 子句中的表名,FROM 子句中写在最后的表 (基础表 driving table) 将被最先处理,在 FROM 子句中包含多个表的情况下,你必须选择记录条数最少的表作为基础表。如果有 3 个以上的表连接查询,那就需要选择交叉表 (intersection table) 作为基础表,交叉表是指那个被其他表所引用的表。(2) WHERE 子句中的连接顺序:ORACLE 采用自下而上的顺序解析 WHERE 子句,根据这个原理,表之间的连接必须写在其他 WHERE 条件之前,那些可以过滤掉最大数量记录的条件必须写在 WHERE 子句的末尾。(3) SELECT 子句中避免使用*:ORACLE 在解析的过程中,会将'*'依次转换成所有的列名,这个工作是通过查询数据字典完成的,这意味着将耗费更多的时间 (4) 减少访问数据库的次数:ORACLE 在内部执行了许多工作:解析 SQL 语句,估算索引的利用率,绑定变量,读数据块等;(5) 在 SQL*Plus , SQL*Forms 和 Pro*C 中重新设置 ARRAYSIZE 参数,可以增加每次数据库访问的检索数据量,建议值为 200 (6) 使用 DECODE 函数来减少处理时间:使用 DECODE 函数可以避免重复扫描相同记录或重复连接相同的表。(7) 整合简单,无关联的数据库访问:如果你有几个简单的数据库查询语句,你可以把它们整合到一个查询中 (即使它们之间没有关系) (8) 删除重复记录:最高效的删除重复记录方法 ( 因为使用了 ROWID) 例子:DELETE FROM EMP E WHERE E.ROWID > (SELECT MIN(X.ROWID) FROM EMP X WHERE X.EMP_NO = E.EMP_NO); (9) 用 TRUNCATE 替代 DELETE: 当删除表中的记录时,在通常情况下,回滚段 (rollback segments ) 用来存放可以被恢复的信息。如果你没有 COMMIT 事务,ORACLE 会将数据恢复到删除之前的状态 (准确地说是恢复到执行删除命令之前的状况) 而当运用 TRUNCATE 时,回滚段不再存放任何可被恢复的信息。当命令运行后,数据不能被恢复。因此很少的资源被调用,执行时间也会很短。(译者按:TRUNCATE 只在删除全表适用,TRUNCATE 是 DDL 不是 DML) (10) 尽量多使用 COMMIT: 只要有可能,在程序中尽量多使用 COMMIT, 这样程序的性能得到提高,需求也会因为 COMMIT 所释放的资源而减少:COMMIT 所释放的资源:a. 回滚段上用于恢复数据的信息。b. 被程序语句获得的锁 c. redo log buffer 中的空间 d. ORACLE 为管理上述 3 种资源中的内部花费(截至 2024 年 4 月 7 日)
ORACLE 多表查询优化
一、FROM 子句后面的表顺序有讲究,ORACLE 在解析 sql 语句的时候对 FROM 子句后面的表名是从右往左解析的,是先扫描最右边的表,然后在扫描左边的表,然后用左边的表匹配数据,匹配成功后就合并。所以,在对多表查询中,一定要把小表写在最右边。例如下面的两个语句:--tableA:100w 条记录 tableB:1w 条记录--执行速度十秒 selectcount(*)fromtableA, tableB;--执行速度百秒甚至更高 selectcount(*)fromtableB, tableA; 还有一种是三张表的查询,例如 selectcount(1)fromtableA a,tableB b ,tableC cwherea.id = b.id and a.id= c.id; 上面中 tableA 为交叉表,根据 oracle 对 From 子句从右向左的扫描方式,应该把交叉表放在最末尾,然后才是最小表,所以上面的应该这样写:--tableA a 交叉表,tabelB b 100w,tableC c 1wselectcount(1)fromtableB b ,tableC c ,tableA awherea.id=b.id and a.id=c.id; 二、ORACLE 对 where 子句后面的条件过滤是自下向上,从右向左扫描的,所以和 From 子句一样一样的,把过滤条件排个序,按过滤数据的大小,自然就是最少数据的那个条件写在最下面,最右边,依次类推,例如:--不可取性能低下 select*fromtableA awherea.id >500and a.lx ='2b'and a.id < (selectcount(1)fromtableAwhereid =a.id)--性能高 select*fromtableA awherea.id < (selectcount(1)fromtableAwhereid = a.id) and a.id >500and a.lx ='2b' 三、使用 select 的时候少用*,写上字段名,因为 ORACLE 的查询器会把*转换为表的全部列名,这个会浪费时间的,所以在大表中少用; 四、充分利用 rowid ,可以用 rowid 来分页,删除查询重复记录,很强大的,给两个例子:--oracle 查找重复记录 select*fromtableA awherea.rowid >= (selectmin(rowid)fromtableB bwherea.column = b.column) -- 分页 start =10limit =10-- end 为 start +limit--1.查询要排列的表 a--2.查询 a 表的 rownum 找出小于 end 的数据组成表 b--3.查询 b 表通过 rownum 找出大于 start 的数据完成--简单的说先根据 end 值过滤数据,然后在根据 start 过滤数据 select*from(selecta.* , rownum rnfrom(select*fromuim_serv_file_data order by ouid ) awhererownum <=20) bwherern >10order by ouid desc 五、存储过程中需要注意的,多用 commit 了,既可以释放资源,但是要谨慎。六、减少对数据库表的查询,这个很重要,能减少就减少,因为在执行语句的时候 oracle 会做很多初始工作。(资料日期为 2024 年 12 月 24 日)
Oracle 数据库性能优化全攻略:十大关键方向深度解析与实践指南
一、SQL 查询优化 SQL 查询优化是提升 Oracle 数据库性能的基础。通过优化 SQL 语句,可以显著减少查询响应时间和系统资源消耗。原理描述:SQL 查询优化的核心在于减少数据访问量和计算量。通过合理的查询设计、索引使用和避免全表扫描,可以大幅提升查询效率。步骤详解:**避免使用 SELECT ***:明确指定需要的列,减少数据传输量。-- 不推荐 SELECT*FROMemployees;-- 推荐 SELECTemployee_id,first_name,last_nameFROMemployees; 一键获取完整项目代码 sql 1 2 3 4 5 使用 WHERE 子句过滤数据:尽早过滤数据,减少处理的数据量。-- 不推荐 SELECT*FROMemployeesWHEREsalary>5000;-- 推荐 SELECTemployee_id,first_name,last_nameFROMemployeesWHEREsalary>5000; 一键获取完整项目代码 sql 1 2 3 4 5 使用索引:在 WHERE 子句和 JOIN 条件中使用索引列,避免全表扫描。-- 创建索引 CREATEINDEXidx_employee_salaryONemployees(salary);-- 使用索引 SELECTemployee_id,first_name,last_nameFROMemployeesWHEREsalary>5000; 一键获取完整项目代码 sql 1 2 3 4 5 避免在 WHERE 子句中使用函数:函数的使用会导致索引失效。-- 不推荐 SELECT*FROMemployeesWHEREUPPER(last_name)='SMITH';-- 推荐 SELECT*FROMemployeesWHERElast_name='Smith'; 一键获取完整项目代码 sql 1 2 3 4 5 使用 EXISTS 代替 IN:EXISTS 通常比 IN 更高效。-- 不推荐 SELECT*FROMemployeesWHEREdepartment_idIN(SELECTdepartment_idFROMdepartmentsWHERElocation_id=1700);-- 推荐 SELECT*FROMemployees eWHEREEXISTS(SELECT1FROMdepartments dWHEREd.department_id=e.department_idANDd.location_id=1700);(2025 年 3 月 20 日的资料)
Oracle 中如何优化 SQL 查询?
1. 索引优化 创建合适的索引:确保经常用于 WHERE 子句、JOIN 条件或 ORDER BY 子句的列上有适当的索引。避免过度索引:过多的索引会增加写操作的成本,并消耗额外的存储空间。定期审查并删除不必要的索引。使用复合索引:对于多列查询,考虑创建复合索引。确保最常用的过滤条件位于复合索引的前面。维护索引:定期重建或重组索引来保持其效率。2.SQL 语句优化 减少全表扫描:尽量通过索引或其他方式减少全表扫描的情况。优化 JOIN 操作:使用 INNER JOIN 而不是 OUTER JOIN(如果适用)。合理安排 JOIN 顺序,通常将较小的表放在前面。考虑使用哈希连接 (HASH JOIN) 或嵌套循环连接 (NESTED LOOPS JOIN),具体取决于数据量和分布。**避免使用 SELECT ***:只选择需要的列,以减少 I/O 开销。使用绑定变量:利用绑定变量来提高 SQL 重用性,减少硬解析。优化子查询:尽可能将子查询转换为 JOIN,或者使用 EXISTS 代替 IN。使用 UNION ALL 而非 UNION:如果不需要去重,使用 UNION ALL 可以提高性能。适当使用临时表:对于复杂的查询,可以考虑使用临时表来简化逻辑。3. 使用 EXPLAINPLAN 分析执行计划:使用 EXPLAIN PLAN FOR 命令来查看 SQL 语句的执行计划,了解查询是如何执行的,并据此进行优化。理解 CBO(Cost-Based Optimizer):了解 CBO 如何估算成本,并基于统计信息做出决策。4. 统计信息 收集准确的统计信息:定期更新表、索引以及列级别的统计信息,以便优化器能够做出更好的执行计划决策。直方图:对于倾斜分布的数据,考虑创建直方图来提供更详细的统计信息给优化器。5. 参数调优 调整初始化参数:根据实际情况调整一些关键的初始化参数,如 db_file_multiblock_read_count、sort_area_size 等。会话级参数:有时也需要针对特定会话调整参数设置。6. 并行处理 启用并行查询:对于大型查询,可以启用并行查询来利用多个 CPU 核心。合理配置并行度:根据系统资源和查询特性合理设置并行度。7. 缓存管理 利用缓存:确保查询结果和常用数据被缓存在 SGA(System Global Area) 中的缓冲区缓存中。调整 PGA 大小:根据工作负载情况调整 PGA(Program Global Area) 大小,特别是对于排序和哈希操作。8. 使用提示 (Hints) 使用 SQL 提示:在必要时使用 SQL 提示来指导优化器选择特定的执行路径。谨慎使用:提示应该谨慎使用,因为它们可能会限制优化器的选择范围,导致次优的执行计划。(撰于 2024 年 9 月 28 日)
FAQ
Oracle 多表查询中 FROM 子句的表顺序有什么讲究?
ORACLE 的解析器按照从右到左的顺序处理 FROM 子句中的表名,FROM 子句中写在最后的表将被最先处理,因此必须选择记录条数最少的表作为基础表写在最右边。
如何优化 WHERE 子句以提高查询效率?
ORACLE 采用自下而上的顺序解析 WHERE 子句,表之间的连接必须写在其他 WHERE 条件之前,那些可以过滤掉最大数量记录的条件必须写在 WHERE 子句的末尾。
为什么建议避免使用 SELECT *?
ORACLE 在解析的过程中,会将'*'依次转换成所有的列名,这个工作是通过查询数据字典完成的,这意味着将耗费更多的时间,明确指定需要的列可减少数据传输量。