Oracle游标

游标的生命周期

打开游标——>解析游标——>定义输出变量——>绑定输入变量——>执行游标——>获取游标——>关闭游标

利用DBMS_SQL包显示编码

DECLARE
   l_ename    EMP.ENAME%TYPE := 'SCOTT';
   l_empno    EMP.EMPNO%TYPE;
   l_cursor   INTEGER;
   l_retval   INTEGER;
BEGIN
   --open
   l_cursor := DBMS_SQL.OPEN_CURSOR;
   --parse
   DBMS_SQL.PARSE (l_cursor, 'select empno from emp where ename=:ename', 1);
   --output variable
   DBMS_SQL.define_column (l_cursor, 1, l_empno);
   --bind variable
   DBMS_SQL.BIND_VARIABLE (l_cursor, ':ename', l_ename);
   --excute
   l_retval := DBMS_SQL.EXECUTE (l_cursor);

   --fetch
   IF DBMS_SQL.FETCH_ROWS (l_cursor) > 0
   THEN
      DBMS_SQL.COLUMN_VALUE (l_cursor, 1, l_empno);
   END IF;

   --close
   DBMS_SQL.CLOSE_CURSOR (l_cursor);
END;

利用隐含游标

DECLARE
   l_ename   EMP.ENAME%TYPE := 'SCOTT';
   l_empno   EMP.EMPNO%TYPE;
BEGIN
   SELECT empno
     INTO l_empno
     FROM emp
    WHERE ename = l_name;
END;

解析的过程

包含VPD的约束条件——>语法语义以及访问权限检查——>将父游标保存到库缓存——>逻辑优化——>物理优化——>将子游标保存到库缓存

v$sqlarea(父)  sql_id (address,hash_value)

v$sql(子)  sql_id,child_number(address,hash_value,child_number)

硬解析成本高的原因:

1,逻辑优化和物理优化非常消耗CPU资源。

2,需要分配内存保存父游标和子游标在库缓存(库缓存在所有session之间共享,内存非配必须串行)。

共享游标

与父游标有关的关键信息是:SQL文本

与子游标有关的关键信息是:执行计划及其有关的执行环境

v$sql_shared_cursor查看游标无法共享的原因

绑定变量

优点:可以共享游标,避免硬解析以及与之相关的额外开销。

缺点:where条件的子句中会一些至关重要的信息对优化器不可见。字面量可以提高估算的准确性

绑定变量窥测(bind variable peeking):在物理优化阶段,优化器会窥测绑定变量的值,将它当做字面量来使用。

缺点是生成的执行计划会依赖第一次生成执行计划所提供的值。

为了解决这个问题,Oracle11g引入一种被称为扩展的游标共享(extended cursor sharing ,也称适用性游标共享adaptive cursor sharing)的新功能。

它的目的是在重用一个共享游标但是会导致效率低下时能够进行自动识别。

Oracle11g v$sql有如下栏位:(10g只有70个栏位,11g有87个栏位
IS_BIND_SENSITIVE,
IS_BIND_AWARE,
IS_SHAREABLE,

最佳实践

不涉及where子句的时候,应该使用绑定变量,直方图信息对优化器有很大影响的情况下,最好不使用绑定变量。

sql处理少量数据,使用绑定变量通常是较优的选择

sql处理大量数据,使用绑定变量对总响应时间几乎没有影响

读写数据块

逻辑读(logical read):服务器进程访问到buffer cache中一个数据块的时候,就发生了一次逻辑读。注意:逻辑读既用于读数据块也用于写数据块。

物理读(physical read):当服务器进程需要访问buffer cache不存在的数据块时产生一次物理读。相应地,它需要打开数据文件,读这个数据块,并放入buffer cache

物理写(physical write):服务器进程不负责写,后台进程DBWR写回数据文件

直接读(direct read)

直接写(direct write)

原文地址:https://www.cnblogs.com/guilingyang/p/6268817.html