RESULT CACHE
发布日期:2021-09-16 04:38:20 浏览次数:49 分类:技术文章

本文共 13970 字,大约阅读时间需要 46 分钟。

Result Cache: 是一块内存区域,要么在sga中,要么在客户端的应用程序内存中,存放了从数据库返回的结果或者查询块的重用,缓存这些行是通过共享sql语句或者session。
Result Cache 可以分为两种;1 服务端结果的缓存
                           2 客户端结果的缓存
                           前者通过服务器端SGA来缓存结果集,后者通过客户端来缓存结果集。
                           
1.1    服务端结果的缓存
服务端result Cache的内存池是在shared pool中,内存池中包含SQL语句查询的缓存结果,以及PL/SQL函数返回的结果缓存,
利用服务端缓存结果的益处,也要取于应用程序。对于OLAP的应用,可以从中得到显著的提升。
那么 server result cache 是如何工作的呢??
 当执行查询,数据库会在result cache中搜索是否有查询结果缓存,如果存在,数据库会在内存中直接检索结果集返回给客户端,
 如果不存在,那么数据库会执行SQL查询,返回结果集给客户端,并且把结果集缓存在result cache中。如果用户不断的执行相同
 的查询和函数,那么数据库会从result cache 中返结果,减少了响应时间。如果修改数据库的对象,那么cache result 的对象就会无效
 
 cache result 
SQL> select *From t1,t2 where t1.deptno=t2.deptno;
已选择12行。
执行计划
----------------------------------------------------------
Plan hash value: 2959412835
---------------------------------------------------------------------------
| Id  | Operation          | Name | Rows  | Bytes | Cost (%CPU)| Time     |
---------------------------------------------------------------------------
|   0 | SELECT STATEMENT   |      |    12 |   708 |     5  (20)| 00:00:01 |
|*  1 |  HASH JOIN         |      |    12 |   708 |     5  (20)| 00:00:01 |
|   2 |   TABLE ACCESS FULL| T2   |     4 |    80 |     2   (0)| 00:00:01 |
|   3 |   TABLE ACCESS FULL| T1   |    12 |   468 |     2   (0)| 00:00:01 |
---------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
   1 - access("T1"."DEPTNO"="T2"."DEPTNO")
统计信息
----------------------------------------------------------
          1  recursive calls
          0  db block gets
         15  consistent gets
          0  physical reads
          0  redo size
       1664  bytes sent via SQL*Net to client
        416  bytes received via SQL*Net from client
          2  SQL*Net roundtrips to/from client
          0  sorts (memory)
          0  sorts (disk)
         12  rows processed
SQL> select  /*+ RESULT_CACHE */ *From t1,t2 where t1.deptno=t2.deptno;
已选择12行。
执行计划
----------------------------------------------------------
Plan hash value: 2959412835
--------------------------------------------------------------------------------------------------
| Id  | Operation           | Name                       | Rows  | Bytes | Cost (%CPU)| Time     |
--------------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT    |                            |    12 |   708 |     5  (20)| 00:00:01 |
|   1 |  RESULT CACHE       | 30vm7tpnnnbrd97wdu9uvp4x1n |       |       |            |          |
|*  2 |   HASH JOIN         |                            |    12 |   708 |     5  (20)| 00:00:01 |
|   3 |    TABLE ACCESS FULL| T2                         |     4 |    80 |     2   (0)| 00:00:01 |
|   4 |    TABLE ACCESS FULL| T1                         |    12 |   468 |     2   (0)| 00:00:01 |
--------------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
   2 - access("T1"."DEPTNO"="T2"."DEPTNO")
Result Cache Information (identified by operation id):
------------------------------------------------------
   1 - column-count=11; dependencies=(SCOTT.T1, SCOTT.T2); name="select  /*+ RESULT_CACHE */ *From t1,t2 where t1.deptno=t2.deptno"
统计信息
----------------------------------------------------------
          1  recursive calls
          0  db block gets
         15  consistent gets
          0  physical reads
          0  redo size
       1664  bytes sent via SQL*Net to client
        416  bytes received via SQL*Net from client
          2  SQL*Net roundtrips to/from client
          0  sorts (memory)
          0  sorts (disk)
         12  rows processed
SQL> select  /*+ RESULT_CACHE */ *From t1,t2 where t1.deptno=t2.deptno;
已选择12行。
执行计划
----------------------------------------------------------
Plan hash value: 2959412835
--------------------------------------------------------------------------------------------------
| Id  | Operation           | Name                       | Rows  | Bytes | Cost (%CPU)| Time     |
--------------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT    |                            |    12 |   708 |     5  (20)| 00:00:01 |
|   1 |  RESULT CACHE       | 30vm7tpnnnbrd97wdu9uvp4x1n |       |       |            |          |
|*  2 |   HASH JOIN         |                            |    12 |   708 |     5  (20)| 00:00:01 |
|   3 |    TABLE ACCESS FULL| T2                         |     4 |    80 |     2   (0)| 00:00:01 |
|   4 |    TABLE ACCESS FULL| T1                         |    12 |   468 |     2   (0)| 00:00:01 |
--------------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
   2 - access("T1"."DEPTNO"="T2"."DEPTNO")
Result Cache Information (identified by operation id):
------------------------------------------------------
   1 - column-count=11; dependencies=(SCOTT.T1, SCOTT.T2); name="select  /*+ RESULT_CACHE */ *From t1,t2 where t1.deptno=t2.deptno"
统计信息
----------------------------------------------------------
          0  recursive calls
          0  db block gets
          0  consistent gets
          0  physical reads
          0  redo size
       1664  bytes sent via SQL*Net to client
        416  bytes received via SQL*Net from client
          2  SQL*Net roundtrips to/from client
          0  sorts (memory)
          0  sorts (disk)
         12  rows processed
     
 SQL> select id,type,OBJECT_NO,ROW_COUNT,BUCKET_NO,ROW_SIZE_MAX  from  V$RESULT_CACHE_OBJECTS;
        ID TYPE        OBJECT_NO  ROW_COUNT  BUCKET_NO ROW_SIZE_MAX
---------- ---------- ---------- ---------- ---------- ------------
         1 Dependency      96284          0       3304            0
         0 Dependency      96098          0       3210            0
         2 Result              0         12       3957           72
         

 

查看server result cache的内存使用报告

SQL> set serveroutput on;

SQL> exec dbms_result_cache.Memory_Report
 
R e s u l t   C a c h e   M e m o r y   R e p o r t
[Parameters]
Block Size          = 1K bytes
Maximum Cache Size  = 85024K bytes (85024 blocks)
Maximum Result Size = 4251K bytes (4251 blocks)
[Memory]
Total Memory = 87426840 bytes [5.428% of the Shared Pool]
 
... Fixed Memory = 68992 bytes [0.004% of the Shared Pool]
... Dynamic Memory = 87357848 bytes [5.424% of the Shared Pool]
....... Overhead = 293272 bytes
....... Cache Memory = 85024K bytes (85024 blocks)
........... Unused Memory = 0 blocks
........... Used Memory = 85024 blocks
............... Dependencies = 89 blocks (89 count)
............... Results = 84935 blocks
................... SQL     = 59063 blocks (46593 count)
................... Invalid = 25546 blocks (23785 count)
 
PL/SQL procedure successfully completed
 
SQL>

DBMS_RESULT_CACHE功能和存储过程

STATUS存储过程

  返回结果缓存的当前状态。值包括:
ENABLED:结果缓存是激活的。
DISABLED:结果缓存是不可用的。
BYPASSED:结果缓存暂时不可用。
SYNC: 结果缓存是可用的,但是目前正与其他RAC节点重新同步。
 
MEMORY_REPORT存储过程
 列出结果缓存内存利用的一个概要(默认)或详细的报表。
 
FLUSH存储过程
 推出整个结果缓存的内容。
 
INVALIDATE存储过程
 使结果缓存中一个特定对象的缓存结果无效。
 
INVALIDATE_OBJECT存储过程
 根据缓存ID使一特定结果缓存无效。

2、服务端缓存的参数
SQL> show parameter result
NAME                                 TYPE        VALUE
------------------------------------ ----------- -------------------
client_result_cache_lag              big integer 3000
client_result_cache_size             big integer 0
result_cache_max_result              integer     5
result_cache_max_size                big integer 3168K
result_cache_mode                    string      MANUAL
result_cache_remote_expiration       integer     0
                                                           
result_cache_mode:
该参数有两个值MANUAL,FORCE;
manaual:默认值是MANUAL.也就是说我们要启用该特性,那么必须通过hint  /*+ RESULT_CACHE */或者table annotation来实现,这是oracle 推荐的值;
force:如果查询的结果不在缓存,那么执行查询然后会把结果缓存中内存中去。如果当设置为force时,同时你又不想某个sql或应用使用该特性,那么可以使用NO_RESUIT_CACHE  hint来不缓存结果。
result_cache_max_size :该参数控制着使用result cache特性的内存大小,当该参数设置为0,那么也就意味着关闭了该特性。
该部分内存是从SGA中分配的,至于分配的比例关系,metalink提供了如下的数据:
0.25% of MEMORY_TARGET or
0.5% of SGA_TARGET or
1% of SHARED_POOL_SIZE
上面的关系应该是一目了然了,如何解释?我暂且不说,给大家留个问题。
result_cache_max_result:该参数是控制单个result所能占据query cache的大小比例,注意是一个百分比。该参数默认是是5%,取值范围当然是1% ~ 100% 了。
result_cache_remote_expiration:该参数的作用是根据远程数据库对象设置缓存过期的时间,默认值为0.也就是说,默认情况下,远程数据库对象不会被进行cache的。
_result_cache_global
顾名思义,该参数肯定是针对Rac集群而设计的,这样可以大大的降低经典的gc等待。
3、管理server cache 的大小
server result cache 的大小设置,由数据库的初始化参数确定或者由DBMS_RESULT_CACHE,默认数据库启动result cache 是在share pool 中分配。result cache 的大小取决于share pool 的大小以及数据库的管理方式来决定
Oracle11g都不会将RESULT_CACHE_MAX_SIZE设置为超过
SHARED_POOL_SIZE的75%,至于分配的比例关系如下:
如果用MEMORY_TARGET来初始化内存大小,那么result cache大小是  0.25% of MEMORY_TARGET or
如果用SGA_TARGET 来初始设定了share pool 大小,那么 result cache 大小是0.5% of SGA_TARGET or
如果使用设定了SHARED_POOL_SIZE的大小,那么result cache 大小是  1% of SHARED_POOL_SIZE
                        
server result cache的大小会增长到RESULT_CACHE_MAX_SIZE,如果查询结果的大小大于result cache 的大小,则不会缓存。
数据库根据LRU算法换入换出cache result。但是不会自动释放result cache内存,可以使用DBMS_RESULT_CACHE.FLUSH                                                            
可以通过调整参数RESULT_CACHE_MAX_SIZE,来调整result cache缓存大小,在rac环境下,每个实例都有自己的result cache,可以给他们设置不同的大小
 但是这样会造成invalidations work across instances. 为了关闭实例 集群的server result cache ,你必须在实例启动前明确的为每个实例设置 RESULT_CACHE_MAX_SIZE= 0 。
 
         
 Server Result Cache
 
EXECUTE DBMS_RESULT_CACHE.MEMORY_REPORT  //获取缓存的使用情况
EXECUTE DBMS_RESULT_CACHE.FLUSH   //清除现有缓存结果
4、client result cache
 客户端缓存只保存最外层查询的结果集,子查询和查询块都不会被缓存。
 
 
在使用OCI应用程序时,可以通过客户端内存来缓存查询的结果集,缓存结果可以在所有session间共享,当查询反复执行时,查询结果可以直接从客户段的缓存中获得,从而极大地提高应用效率。
客户端结果集缓存并不使用服务器端的内存,不会对服务器的内存使用造成影响,这一点和Server Result Cache不同。
同Client Result Cache相关的视图主要有:
SQL> select * from dict where table_name like '%CLIENT_RESULT_CACHE%';
TABLE_NAME                    COMMENTS
------------------------------ ---------------------------------------------
CLIENT_RESULT_CACHE_STATS$    Synonym for CRCSTATS_$
GV$CLIENT_RESULT_CACHE_STATS  Synonym for GV_$CLIENT_RESULT_CACHE_STATS
V$CLIENT_RESULT_CACHE_STATS    Synonym for V_$CLIENT_RESULT_CACHE_STATS
同Client Result Cache相关的参数有:
SQL> show parameter client_result
NAME                                TYPE        VALUE
------------------------------------ ----------- ------------------------------
client_result_cache_lag              big integer 3000
client_result_cache_size            big integer 0
CLIENT_RESULT_CACHE_SIZE:给每个进程设置最大的缓存,如果要打开客户端缓存,最小设置此参数为 32768 bytes ,如果小于这个参数值就是关闭客户端缓存。
CLIENT_RESULT_CACHE_LAG:设置客户端缓存结果的延时时间,如果客户端和数据库交互不频繁,可以设置此参数值比较小
COMPATIBLE :版本兼容性
5 使用hint 缓存结果
 result cache mode 是手工方式 MANUAL,那么可以使用hint  /*+ RESULT_CACHE */提示,让数据库缓存cache the results of a query block and to use the cached results in future executions
 /*+ NO_RESULT_CACHE */ 提示不要缓存结果在客户端或者是服务端 
RESULT_CACHE 提示只能在指定hint的sql中缓存查询块,如果hint 在视图中,那么只缓存结果,下列类型的视图会被缓存。
1、The view must be a standard view (a view created with the CREATE ... VIEW statement), an inline view specified in the FROM clause of 
 a SELECT statement, or an inline view created with the WITH clause.
2 、The result of a view query with a correlated column, which is a reference to an outer query block, cannot be cached.
3 Query results are stored in the server result cache, not the client result cache.
4 A caching view is not merged into its outer (or referring) query block. Adding the RESULT_CACHE hint to inline views disables 
 optimizations between the outer query and inline view to maximize reusability of the cached result.
SELECT * 
FROM   ( SELECT /*+ RESULT_CACHE */ department_id, manager_id, count(*) count 
         FROM   hr.employees 
         GROUP BY department_id, manager_id ) view1 
WHERE  department_id = 30;
因为RESULT_CACHE hint指定缓存内联块,查询结果在外层,那么外层结果是不会被缓存的,但是内层缓存块是会被缓存在服务端
WITH view2 AS
( SELECT /*+ RESULT_CACHE */ department_id, manager_id, count(*) count 
  FROM hr.employees 
  GROUP BY department_id, manager_id ) 
SELECT *
FROM   view2 
WHERE  count BETWEEN 1 and 5;
6 Table Annotations
你也可以使用表注释来控制sql语句结果的缓存,Table annotations are in effect only for the whole query, not for query segments.这样的好处在与避免了应用程序级别添加hint
table annotation  < SQL hint
table annotation 的优先级小于sql hint,所以你可以使用sql hint 覆盖  表级或者session 级别的table annotation
DEFAULT
If at least one table in a query is set to DEFAULT, then result caching is not enabled at the table level for this query, unless the RESULT_CACHE_MODE initialization parameter 
is set to FORCE or the RESULT_CACHE hint is specified. This is the default value.
---如果一个查询中有一个表是default,那么这个查询在表级就没有开启缓存,除非RESULT_CACHE_MODE 在初始化参数时设置为force,或者使用 RESULT_CACHE hint。
FORCE
If all the tables of a query are marked as FORCE, then the query result is considered for caching. The table annotation FORCE takes precedence over the 
RESULT_CACHE_MODE parameter value of MANUAL set at the session level.
---如果一个查询的所有表都是force,那么这个查询就会被设置为缓存,table annotation=force 在session 界别的优先级高于RESULT_CACHE_MODE =manual。
举例:
CREATE TABLE sales (...) RESULT_CACHE (MODE DEFAULT); ---这样的表就不会被缓存因为mode 是default
ALTER TABLE sales RESULT_CACHE (MODE FORCE);  ---修改表为force
SELECT   prod_id, SUM(amount_sold) FROM     sales  GROUP BY prod_id  HAVING   prod_id=136;
---此查询适合频繁被查询,并且返回行数很少,这种类型的适合 Table Annotations
SELECT   /*+ NO_RESULT_CACHE */ *  FROM     sales  ORDER BY time_id DESC;
---此种查询适合查询次数比较少,返回行数比较多的查询
7.在下列情况下,不能被缓存
You cannot cache results when the following objects or functions are in a query:
  1、Temporary tables and tables in the SYS or SYSTEM schemas
  2、Sequence CURRVAL and NEXTVAL pseudo columns
  3、SQL functions CURRENT_DATE, CURRENT_TIMESTAMP, LOCAL_TIMESTAMP, USERENV/SYS_CONTEXT (with non-constant variables), SYS_GUID, SYSDATE, and SYS_TIMESTAMP
8 缓存读一致的要求
  1、The read-consistent snapshot used to build the result must retrieve the most current committed state of the data.
  2、The query points to an explicit point in time using flashback query.
9、查询结果缓存参数化要求
Cache results can be reused when they are parameterized with variable values when queries are equivalent and the parameter values are the same. 
Different values or bind variable names may cause cache misses. Results are parameterized if any of the following constructs are used in the query:
   1、Bind variables
   2、The SQL functions DBTIMEZONE, SESSIONTIMEZONE, USERENV/SYS_CONTEXT (with constant variables), UID, and USER
   3、NLS parameters

10 常用查询表
V$RESULT_CACHE_STATISTICS:列出服务端缓存设置和内存使用的统计信息
V$RESULT_CACHE_MEMORY:列出所有服务端内存块缓存和相应的统计结果
V$RESULT_CACHE_OBJECTS:列出服务端缓存的对象,以及属性
V$RESULT_CACHE_DEPENDENCYL:列出服务端缓存依赖的细节
CLIENT_RESULT_CACHE_STATS$
DBA_TABLES, USER_TABLES, ALL_TABLES
SELECT NAME, VALUE  FROM   V$RESULT_CACHE_STATISTICS;   --列出服务端缓存的统计信息
SELECT STAT_ID, SUBSTR(NAME,1,20), VALUE, CACHE_ID  FROM   CLIENT_RESULT_CACHE_STATS$  ORDER BY CACHE_ID, STAT_ID; --监控客户端缓存的统计信息

检查result cache配置是否生效

1.select dbms_result_cache.status from dual;
2.dbms_result_cache.MEMORY_REPORT
3.查看sql执行计划

注意:

11g的active dataguard的备库是不能使用result cache的,这是oracle的一个bug,因为涉及到内码的问题,所以oracle一直没有修复,result cache目前可以使用在单节点主库和rac环境。

关于这个新特性的参考链接:
http://docs.oracle.com/cd/E11882_01/server.112/e41573/memory.htm#PFGRF983
http://www.ningoo.net/2007/08/22/oracle11g_new_feature_server_result_cache2.htm
http://yangtingkun.itpub.net/post/468/391015
http://yangtingkun.itpub.net/post/468/391560
 

检查result cache配置是否生效

1.select dbms_result_cache.status from dual;
2.dbms_result_cache.MEMORY_REPORT
3.查看sql执行计划

注意:

11g的active dataguard的备库是不能使用result cache的,这是oracle的一个bug,因为涉及到内码的问题,所以oracle一直没有修复,result cache目前可以使用在单节点主库和rac环境。

转载地址:https://blog.csdn.net/wll_1017/article/details/45314943 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!

上一篇:Which two are the uses of the ASM metadata backup and restore (AMBR) feature? (Choose two.)
下一篇:linux top 命令详解

发表评论

最新留言

留言是一种美德,欢迎回访!
[***.207.175.100]2024年03月23日 13时40分11秒