ORACLE实际执行计划与预估执行计划不一致性能优化案例

简介: 在一台ORACLE服务器上做巡检时,使用下面SQL找出DISK_READ最高的TOP SQL分析时,分析过程中,有一条SQL语句的一些反常现象,让人觉得很奇怪:   SELECT SQL_ID,       SQL_TEXT,        DISK_READS,        BUF...

 

在一台ORACLE服务器上做巡检时,使用下面SQL找出DISK_READ最高的TOP SQL分析时,分析过程中,有一条SQL语句的一些反常现象,让人觉得很奇怪:

 

SELECT SQL_ID,
       SQL_TEXT, 
       DISK_READS, 
       BUFFER_GETS, 
       PARSING_SCHEMA_NAME, 
       EXECUTIONS 
FROM   V$SQLAREA 
ORDER  BY DISK_READS DESC; 

 

在SQL Developer中查看SQL的预估执行计划,发现执行计划走INDEX UNIQUE SCAN,而且IO COST其实不高。如下所示,而且执行次数也不是非常多,那么推断:很有可能这个SQL的实际执行计划跟预估的执行计划有很大偏差。

 

SELECT 
 "Extent1"."SC_NO" AS "SC_NO", 
 "Extent1"."CUSTOMER_CD" AS "CUSTOMER_CD", 
 "Extent1"."FACTORY_CD" AS "FACTORY_CD", 
 "Extent1"."REQ_USER_ID" AS "REQ_USER_ID", 
 "Extent1"."REQ_USER_GRP_ID" AS "REQ_USER_GRP_ID"
 FROM "SC_HD" "Extent1"
 WHERE ("Extent1"."SC_NO" = :p__linq__0) AND (ROWNUM <= (1) )

 

 

 

clip_image001[4]

 

 

于是根据SQL_ID生成了对应SQL的awrsqrpt报表,如下截图所示,实际执行计划确实是全表扫描,Buffer Gets与Disk Reads也很高

 

 

clip_image002[4]

 

 

在sqltrpt.sql里面分析查看该SQL时,如下所示, 可以发现其绑定变量存在隐式转换(implicit data type conversion),导致执行计划走全表扫描

 

 

clip_image003[4]

 

 

于是分析了一下绑定变量的类型,发现:P__LINQ__0的类型为NVARCHAR(32) 而实际上字段SC_NO为VARCHAR(16),所以肯定是应用程序里面给该绑定变量赋值出现了问题。

 

SQL> COL NAME FOR A32;
SQL> COL DATATYPE_STRING FOR A20;
SQL> COL VALUE_STRING FOR A20;
SQLSELECT NAME, DATATYPE_STRING, VALUE_STRING
  2   FROM v$sql_bind_capture 
  3   WHERE SQL_ID='&SQL_ID' ;
Enter value for sql_id: dhg6qnxv9c4nz
old   3:  WHERE SQL_ID='&SQL_ID'
new   3:  WHERE SQL_ID='dhg6qnxv9c4nz'
 
NAME                             DATATYPE_STRING      VALUE_STRING
-------------------------------- -------------------- --------------------
:P__LINQ__0                      NARCHAR2(32)         GS17K16005
 
SQL> 

 

后面开发人员协助检查发现,因为这个SQL是代码中Lambda表达式自动生成,后面在Property中设置了字段类型以及长度,问题解决。

 

 

            //SC_HD

            modelBuilder.Entity<SC_HD>().ToTable("SC_HD", OracleSchema);

            modelBuilder.Entity<SC_HD>().HasKey(x => x.SC_NO);

 

 

clip_image004[4]

相关文章
|
6月前
|
JavaScript 前端开发 Java
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——Jsp页面
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——Jsp页面
|
6月前
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——OpSessionview实现
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——OpSessionview实现
|
6月前
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——EmpDao层代码
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——EmpDao层代码
|
6月前
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——Dept实体类和对应的配置信息
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——Dept实体类和对应的配置信息
|
6月前
|
Java
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——Action的实现类
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——Action的实现类
|
6月前
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——工具类
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——工具类
|
6月前
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——DeptDao层代码
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——DeptDao层代码
|
6月前
|
XML Java 数据库连接
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——hibernate的config文件(hibernate.cfg.xml)
struts+hibernate+oracle+easyui实现lazyout组件的简单案例——hibernate的config文件(hibernate.cfg.xml)
|
12天前
|
存储 Oracle 关系型数据库
数据库数据恢复—Oracle ASM磁盘组故障数据恢复案例
Oracle数据库数据恢复环境&故障: Oracle ASM磁盘组由4块磁盘组成。Oracle ASM磁盘组掉线 ,ASM实例不能mount。 Oracle数据库故障分析&恢复方案: 数据库数据恢复工程师对组成ASM磁盘组的磁盘进行分析。对ASM元数据进行分析发现ASM存储元数据损坏,导致磁盘组无法挂载。
|
15天前
|
监控 Oracle 关系型数据库
Oracle数据库性能优化
【10月更文挑战第16天】Oracle数据库性能优化是
14 1

推荐镜像

更多