捕获非绑定变量的SQL语句

之前一直用如下sql来查看非绑定变量的sql,但是不准

select hash_value, substr(sql_text, 1, 80)
  from v$sqlarea
 where substr(sql_text, 1, 40) in
       (select substr(sql_text, 1, 40)
          from v$sqlarea
        having count(*) > 1
         group by substr(sql_text, 1, 40));

SELECT substr(sql_text, 1, 80), count(1)
  FROM v$sql
 GROUP BY substr(sql_text, 1, 80)
HAVING count(1) > 1
 ORDER BY 2;

10g之后,oracle对v$sql视图进行了变更,添加了一个新的字段FORCE_MATCHING_SIGNATURE该字段oracle对于其解释为The signature used when the CURSOR_SHARING parameter is set to FORCE

初步的理解应该是假定数据库的cursor_sharing为force时计算得到的值,

而EXACT_MATCHING_SIGNATURE的解释为Signature calculated on the normalized SQL text. The normalization includes the removal of white space and the uppercasing of all non-literal strings.

个人的理解为当sql语句进入数据库中时对于一些可以潜在可以共享或者因为绑定变量问题造成游标没有共享的sql他的FORCE_MATCHING_SIGNATURE值完全相同,而EXACT_MATCHING_SIGNATURE值是不同的

下面在11gr2中做个测试:

[email protected] SQL>select * from test;

    DEPTNO DNAME          LOC
---------- -------------- -------------
        10 ACCOUNTING     NEW YORK
        20 RESEARCH       DALLAS
        30 SALES          CHICAGO
        40 OPERATIONS     BOSTON

[email protected] SQL>alter system flush shared_pool;

System altered.

[email protected] SQL>select * from test where deptno=10;

    DEPTNO DNAME          LOC
---------- -------------- -------------
        10 ACCOUNTING     NEW YORK

[email protected] SQL>select * from test where deptno=20;

    DEPTNO DNAME          LOC
---------- -------------- -------------
        20 RESEARCH       DALLAS

[email protected] SQL>select * from test where deptno=30;

    DEPTNO DNAME          LOC
---------- -------------- -------------
        30 SALES          CHICAGO

[email protected] SQL>select * from test where deptno=‘10‘;

    DEPTNO DNAME          LOC
---------- -------------- -------------
        10 ACCOUNTING     NEW YORK

[email protected] SQL>select * from test where deptno=‘20‘;

    DEPTNO DNAME          LOC
---------- -------------- -------------
        20 RESEARCH       DALLAS

[email protected] SQL>select * from test where deptno=‘30‘;

    DEPTNO DNAME          LOC
---------- -------------- -------------
        30 SALES          CHICAGO

[email protected] SQL>var v_id number
[email protected] SQL>exec :v_id := 10

PL/SQL procedure successfully completed.

[email protected] SQL>select * from test where deptno=:v_id;

    DEPTNO DNAME          LOC
---------- -------------- -------------
        10 ACCOUNTING     NEW YORK

[email protected] SQL>exec :v_id := 20

PL/SQL procedure successfully completed.

[email protected] SQL>select * from test where deptno=:v_id;

    DEPTNO DNAME          LOC
---------- -------------- -------------
        20 RESEARCH       DALLAS

[email protected] SQL>exec :v_id := 30

PL/SQL procedure successfully completed.

[email protected] SQL>select * from test where deptno=:v_id;

    DEPTNO DNAME          LOC
---------- -------------- -------------
        30 SALES          CHICAGO

[email protected] SQL>set line 123
[email protected] SQL>col sql_text format a40
[email protected] SQL>set numwidth 30
[email protected] SQL>select sql_text,FORCE_MATCHING_SIGNATURE,EXACT_MATCHING_SIGNATURE FROM V$SQL WHERE sql_text like ‘%select * from test%‘;

SQL_TEXT                                       FORCE_MATCHING_SIGNATURE       EXACT_MATCHING_SIGNATURE
---------------------------------------- ------------------------------ ------------------------------
select * from test where deptno=20                  1674223644458057282            5701787720123824641
select * from test where deptno=‘20‘                1674223644458057282            6624213459289620561
select * from test where deptno=‘30‘                1674223644458057282           15799720645668840753
select * from test where deptno=‘10‘                1674223644458057282            7423854019058606662
select * from test where deptno=30                  1674223644458057282            6295409922938069091
select * from test where deptno=10                  1674223644458057282            5918141949209886904
select * from test where deptno=:v_id               5038495461207490287            5038495461207490287

[email protected] SQL>show parameter cursor_shar

NAME                                 TYPE        VALUE
------------------------------------ ----------- ------------------------------
cursor_sharing                       string      EXACT

可以看到以上的sql在没有使用绑定变量的sql中FORCE_MATCHING_SIGNATURE值均是相同的而EXACT_MATCHING_SIGNATURE是不同的那么通过以上的sql我们就可以完善出查找没有使用绑定变量的sql语句:

[email protected] SQL>select *
  2    from (select sql_text,
  3                 row_number() over(partition by FORCE_MATCHING_SIGNATURE order by FORCE_MATCHING_SIGNATURE) rn
  4            from v$sql
  5           where FORCE_MATCHING_SIGNATURE > 0
  6             and FORCE_MATCHING_SIGNATURE != EXACT_MATCHING_SIGNATURE)
  7   where rn > 1;

SQL_TEXT                                                             RN
---------------------------------------- ------------------------------
select * from test where deptno=‘30‘                                  2
select * from test where deptno=‘20‘                                  3
select * from test where deptno=10                                    4
select * from test where deptno=30                                    5
select * from test where deptno=20                                    6

参考:关于高效捕获数据库非绑定变量的SQL语句

时间: 2024-10-08 04:58:02

捕获非绑定变量的SQL语句的相关文章

使用EXECUTE IMMEDIATE来生成含有绑定变量的SQL

一个SQL,通过SPM固定它的执行计划,可以通过DBMS_SPM.LOAD_PLANS_FROM_CURSOR_CACHE实现.也可以通地此功能在不修改原SQL的情况下对其加HINT来固定执行计划.DB VERSION:Oracle 11.2.0.4OS:CentOS 6.6例如:原SQL走索引:SELECT * FROM SCOTT.TB_SPM WHERE OBJECT_ID=10;想通过加HINT让其走全表扫描:SELECT /*+FULL(TB_SPM)*/* FROM SCOTT.TB

Oracle 10g中一个关于绑定变量和非绑定变量的测试对比

首先创建测试表并记录解析统计数据: 进行循环插入数据,以下代码并未使用绑定变量: 发现在增加了11个硬解析. 查询v$sqlarea视图,可以找到这些不能共享的SQL,注意每条SQL都只执行了一次,这些SQL不仅解析要消耗密集的SQL资源,也要占用共享内存存储这些不同的SQL代码: 重建测试表,进行第二次测试: 这一次使用绑定变量,同样10次数据插入: 现在看一下SQL解析的统计数据库,硬解析由原来的145增加到147. 对于该SQL,共享池中只存在一份,解析一次,执行10次,这就是绑定变量的优

python数据库连接之pyMysql -(二):使用变量向SQL语句中传递参数

使用MySQLdb连接数据库执行sql语句时,有以下几种传递参数的方法: 一.通过自定义参数传递: import pymysql import types dbinfo={"host":"192.168.6.41", "user":"lrtsaudio", "password":"2&Ty3DW75i!(vgo.l3Odp1fgWgEG", "db":&quo

通过重新生成执行计划解决绑定变量执行计划偏差导致SQL执行时间过长

基本要素(时间.用户.问题) 用户11g环境下有段SQL语句在程序中执行效率非常差,但是在plsql中执行却很快,通过查看执行计划,发现使用了不同的索引导致,程序中执行的如下: PLSQL中执行的效果如下: 可以看到差别,使用门诊费用记录_IX_登记时间索引是在plsql中的执行计划,使用门诊费用记录_UQ_NO的是程序中的执行计划,两者SQL是完全相同的,唯一却别就是前者使用了绑定变量,后者是直接带参数值执行. 问题分析 问题很明显,由于绑定变量生成的执行计划与实际有偏差,11g本来有个绑定变

OTL翻译(9) --常量的SQL语句

常量的SQL语句 一个没有绑定变量的SQL语句.SQL语句块或是存储过程就被称为常量的SQL语句.OTL通过一个静态的函数来执行这样的SQL语句. 例如: // static otl_cursor::direct_exec() otl_cursor::direct_exec (db, // connect object "create table test_tab(f1 int, f2 varchar(30))" ); // create table otl_cursor::direc

OTL翻译(5) -- otl_stream流相关绑定变量

声明绑定变量 本章节将详细的说明如何在otl_stream流里面声明绑定变量. SQL语句.SQL语句块或存储过程在程序里面使用的时候总是带有占位符.OTL里面带有一个小的解析器用来解析这些占位符,并且在内部进行变量的内存分配操作. 在ORACLE里面占位符的表示方法与其他数据库不同,在ORACLE里面的占位符是通过带有冒号的前缀来表示的,如::f1/:supervisor_name/:employee_id等,并且同一个占位符可能在同一个SQL语句里面使用多次. 在ODBC或DB2 CLI里面

MySQL高级特性——绑定变量

从MySQL 4.1 版本开始,就支持服务器端的绑定变量,这大大提高了客户端和服务器端数据传输的效率 介绍 当创建一个绑定变量 SQL 时,客户端会向服务器发送一个SQL语句的原型.服务器端收到这个SQL语句框架后,解析并存储这个SQL语句的部分执行计划,返回个客户端一个 SQL 语句处理句柄.以后每次执行这类查询,客户端都指定使用这个句柄. 绑定变量的SQL,使用问号标记可以接受参数的位置,当真正需要执行具体查询的时候,则使用具体值来替代这些问号.例如,下面是一个绑定变量的SQL语句: INS

一个11G 抓没有绑定变量的语句.非常好!非常精确,非常快.

--追踪共享池没有绑定变量的SQLSELECT FORCE_MATCHING_SIGNATURE,to_char(FORCE_MATCHING_SIGNATURE ) as sing,       COUNT(1) AS REPLACE_NUM,       ROUND(SUM(SHARABLE_MEM) / 1024 / 1024) AS SHARED_MB,       ROUND(SUM(PERSISTENT_MEM) / 1024 / 1024) AS SHARED_MB,       

SQL Server捕获发生The query processor ran out of internal resources and could not produce a query plan...错误的SQL语句

最近收到一SQL Server数据库服务器的告警邮件,告警内容具体如下所示: DATE/TIME: 10/23/2018 4:30:26 PM DESCRIPTION:  The query processor ran out of internal resources and could not produce a query plan. This is a rare event and only expected for extremely complex queries or querie