关于oracle result_cache

结果集缓存

和聚合物化视图类似,报表系统和数据仓库系统是最适合结果集缓存的,这些系统通常具有大量复杂的SQL,其中不少子查询包含聚合函数,如果能够尽可能重用这些已经计算过的聚合结果集,将极大的提升系统性能并降低服务器负载。默认情况下,服务端结果集大小为共享池大小的0.5%,如果人工设置了共享池大小,则为1%,如果默认值不合适,可以调整result_cache_max_size,该参数声明了用于结果集缓存的SGA大小,将该值更改为0可以禁用结果集缓存,此时通常是应用使用了物化视图进行聚合查询优化或没有很多聚合查询的OLTP系统。需要注意的是,结果集缓存默认是否启用由result_cache_mode控制,参数声明了Oracle如何管理结果集缓存的使用,默认为MANUAL,也就是SQL语句必须使用优化器提示才能使用结果集缓存;当设置为FORCE时表示所有独立执行的语句都可以认为结果集缓存的候选。相对于聚合物化视图可以针对整个表进行聚合,具体查询中可以使用不同的group by字段作为条件重写,结果集缓存只能根据具体的绑定变量进行,由于对子查询块抽象和判断是否共用的成本较高,所以直接基于SQL块的结果集缓存效果性价比在大部分情况下不算很好。

不过11g中PL/SQL函数新增的RESULT_CACHE子句更加有价值,传统的DETERMINISTIC选项仅对于当前SQL语句引用的函数有效,而且不支持PL/SQL函数中调用其他PL/SQL函数。RESULT_CACHE刚好弥补了DETERMINISTIC的弱项,它使得在多个会话、不同的RAC节点、PL/SQL块中都可以重用某个PL/SQL函数的执行结果,其使用如下:

create or replace function getXXXdays(v_tenantid    in varchar2,

                                           v_fundcode    in varchar2,

                                           v_agencyno    in varchar2,

                                           v_currentdate in varchar2,

                                           n_offset      in number,

                                           n_skip        in number := 1,

                                           v_ageregion   in number := 0)

  return number deterministic

  RESULT_CACHE RELIES_ON(ta_thkopenday)  --只要加上RESULT_CACHE RELIES_ON子句即可,依赖数据源可以有多个,多个之间逗号分隔

  is

  result number(8);

begin

end;

/

我们有不少逻辑调用了一个计算交易日期的函数,这个函数又调用了其他很多函数,类似于下面的引用关系:

getintervaldays

       gethkliqdays

              gethkrealdays

       getliqdays

              getrealdays

我们仅通过为各函数增加RESULT_CACHE子句,性能就提升了10%。

如果启用了结果集缓存特性,还需要注意,每个结果集缓存可用的内存大小并不是整个结果集缓存大小,而是受RESULT_CACHE_MAX_RESULT参数控制,其默认为RESULT_CACHE_MAX_SIZE的5%,因为结果集缓存本身的目的并非缓存大型SQL或子查询的结果,所以通常最多增加到10%就足够了,最后应定期监控v$result_cache_statistics和v$result_cache_objects确定结果集缓存的效果,以及是否有必要继续开启结果集缓存,还需要注意不要过多的在高并发的存储过程以及函数上依赖于结果集缓存,它可能会导致latch free竞争严重,进而适得其反造成性能下降。

原文地址:https://www.cnblogs.com/zhjh256/p/10062187.html