Buffer cache 的調整與優化(二)
--********************************
-- Buffer cache 的調整與優化(二)
--********************************
Buffer cache 實際上細分為多個不同的Buffer cache,如keep pool,recycle pool,default pool,下面描述不同buffer cache的使用。
有關Buffer cache 的總體描述,請參考:Buffer cache 的調整與優化(一)
一、不同buffer pool的應用
一個buffer pool即對應於一個oracle 資料塊,三種不同的pool實際上是針對在data buffer cache中塊的訪問的程度不同在通常的
慣例下采取的方法。即對最熱塊,次熱快,以及冷塊存放到不同的buffer pool中。實際上這幾個不同的buffer pool除了分配的大小不同
之外,所採用的演算法都是LRU演算法,因此對塊的快取以及淘汰(aged out)演算法實質一樣。
任意一個不同的buffer pool都將根據訪問方式的不同而只快取讀取到的資料塊,即如果是全表掃描,則快取所有塊,如果是索引快速
掃描,則快取索引的所有葉節點塊。
keep buffer cache --對應keep pool
recycle buffer cache --對應recycle pool
nk buffer caches --對應db_nk_cache_size
default buffer cache --對應dafault pool
keep pool:
對於經常訪問的小表將其常駐記憶體,即放置到keep pool。其作用是保證這部分經常訪問的資料能夠常駐記憶體而不被替換出記憶體,
從而提高訪問這些資料的速度。這個池最好能夠保持99%的命中率,也就是說要保證這個池的大小能夠快取放於這個池的大部分物件。
recycle pool:
對於不經常訪問的大segment,就可以考慮將其放置到recycle pool,以儘快將其淘汰出去。
dafault pool:
普通物件的緩衝池,那些沒有在keep pool也沒有在recycle pool的物件將緩衝到這裡。
nk buffer caches
主要適用於不同平臺傳輸表空間,或根據業務需要來使用非標準表空間之外的表空間。
如磁碟上資料檔案的最小I/O單元叫block一樣,buffer cache的最小單元(或者說結構)叫buffer。
每個buffer跟x$bh中每條記錄存在一一對應關係。
注意:
default buffer cache = db_cache_size - db_keep_cache_size - db_recycle_cache_size - db_nk_cache_size
sys@ORCL> select * from v$version where rownum < 2;
BANNER
----------------------------------------------------------------
Oracle Database 10g Enterprise Edition Release 10.2.0.1.0 - Prod
sys@ORCL> select name,bytes/1024/1024 from v$sgainfo where name='Buffer Cache Size';
NAME BYTES/1024/1024
------------------------- ---------------
Buffer Cache Size 192
sys@ORCL> select name,current_size,buffers,block_size FROM v$buffer_pool;
NAME CURRENT_SIZE BUFFERS BLOCK_SIZE
--------------- ------------ ---------- ----------
DEFAULT 192 23952 8192
sys@ORCL> alter system set db_recycle_cache_size=16m;
sys@ORCL> alter system set db_keep_cache_size=16m;
sys@ORCL> select name,current_size,buffers,block_size FROM v$buffer_pool;
NAME CURRENT_SIZE BUFFERS BLOCK_SIZE
--------------- ------------ ---------- ----------
KEEP 16 1996 8192
RECYCLE 16 1996 8192
DEFAULT 160 19960 8192
sys@ORCL> alter system set db_16k_cache_size=4m;
sys@ORCL> select name,current_size,buffers,block_size FROM v$buffer_pool;
NAME CURRENT_SIZE BUFFERS BLOCK_SIZE
--------------- ------------ ---------- ----------
KEEP 16 1996 8192
RECYCLE 16 1996 8192
DEFAULT 160 19960 8192
DEFAULT 4 252 16384
從上面的設定可以看出,任意一個buffer pool大小的調整,不影響整個buffer_pool的大小。即任意buffer pool的增加,將使得
default buffer pool的減小,反之,任意buffer pool尺寸的減少,default buffer pool的尺寸將會增加。
其次,任意buffer pool的增加應考慮到Oracle 以及OS是否有足夠的記憶體來進行分配。如果是使用了ASMM管理,則應考慮整個
sga_target < sga_max_size。
二、大表段、大索引段隨機訪問的問題
當使用LRU演算法時,對於大表段,索引段的隨機訪問,容易導致其他的並非最頻繁訪問的熱點塊從cache中被aged out.此外,這些隨機訪問
的資料塊並不屬於熱塊,也很容易隨時被替換,通過下面的三種方法來避免該情況的產生:
1.如果受影響的物件是索引,則判斷是否是精確的索引選擇,如果不是,則調整SQL語句。
2.如果SQL語句已優化,則可以將被訪問的大段存放到recycle cache中。
3.可以將一些小的熱點塊移入到keep buffer pool,keep buffer pool能夠最小化cache的丟失。
三、多個buffer pool的設定
db_cache_size
db_keep_cache_size
db_recycle_cache_size
db_nk_cache_size
以上的引數為動態引數,使用下面的方式來調整,可以基於記憶體調整,也可以將引數更改到spfile。
alter system set db_keep_cache_size=nm scope = both | memory | spfile;
alter system set db_16k_cache_size=nm;
alter system set db_recycle_cache_size=nm;
閂由Oracle RDBMS來自動分配
進行了上述設定之後,可以基於這些不同的緩衝池來建立物件
create index idx_obj
storage(buffer_pool keep);
alter table tb_obj
storage(buffer_pool recycle);
alter index idx_obj
storage(buffer_pool keep);
注:
四個池除了使用不同的名稱且產生不同的作用之外,其內部演算法實質是一樣的,都是採用LRU演算法。
一個segment只能放入到一個buffer pool中.如果一個表或索引物件擁有多個segment,則不同的segment可以存放到不同的buffer pool.
如何決定什麼樣的segment存放到何種buffer cache則根據業務需求來定。
如果沒有指定buffer_pool短語,則表示該物件進入default型別的buffer cache。
四、keep buffer pool的使用與優化
將常用的小表物件常駐記憶體
一般情況是物件的大小應當為少於default buffer pool 大小的10%。
根據下面的方法計算物件所佔用塊的總數,且該塊的總數大小應當小於於keep buffer pool的大小。
計算所有將要放入到keep buffer cache物件的總塊數得到一個近似值,然後將稍微大於該近似值的尺寸指定給keep buffer pool。
可以通過查詢DBA_TABLES.BLOCKS 和DBA_TABLES.EMPTY_BLOCKS 獲得塊的資訊或者通過V$BH檢視segment所佔用的buffer。
對於放入keep buffer pool中的表資料,如果物件塊多於buffer pool數量,則以buffer pool數量為準進行快取,冷塊將被新塊置換。
注:如果位於keep buffer pool中的物件尺寸增大,將不會被填充到keep buffer pool。
其次,如果有多個物件快取到keep buffer pool,而keep buffer pool不足以快取這些物件,按LRU演算法,先前位於keep buffer
pool 的物件一樣會被aged out。
首先使用包收集物件資訊
sys@ORCL> exec dbms_stats.gather_table_stats('SCOTT','BIG_KEEP');
sys@ORCL> select table_name,blocks,empty_blocks
2 from dba_tables where owner='SCOTT' and table_name='BIG_KEEP';
TABLE_NAME BLOCKS EMPTY_BLOCKS
------------------------- ---------- ------------
BIG_KEEP 180 0
設定keep buffer pool的大小
alter system set db_keep_cache_size=16m scope = both ; --注意,該引數值的大小應根據實際情況設定
將物件放置的keep buffer pool
alter table big_keep
storage(buffer_pool keep);
五、recycle buffer pool的使用與優化
一旦事務被提交則這些塊將從recycle buffer pool中被清除
物件的大小應當為多於default buffer pool 大小的兩倍
recycle buffer pool需要具有一個事務所需要的全部塊
下面將big_temp 置入到recycle buffer pool
sys@ORCL> exec dbms_stats.gather_table_stats('SCOTT','BIG_RECYCLE');
scott@ORCL> select blocks,empty_blocks from dba_tables
2 where table_name='BIG_RECYCLE' and owner='SCOTT';
BLOCKS EMPTY_BLOCKS
---------- ------------
1062 0
alter system set db_recycle_cache_size=16m scope = both ; --注意,該引數值的大小應根據實際情況設定
scott@ORCL> alter table big_recycle
2 storage(buffer_pool recycle);
使用檢視v$cache,
SELECT owner#
,NAME
,COUNT(*) blocks
FROM v$cache
GROUP BY owner#,NAME;
SELECT s.username --跟蹤recycle buffer pool的I/O情況
,io.block_gets
,io.consistent_gets
,io.physical_reads
FROM v$sess_io io,v$session s
WHERE io.sid=s.sid;
六、獲得buffer pool中的相關資訊
檢視v$bh(基於檢視x$bh)顯示當前位於SGA中所有塊的詳細資訊。決定哪個段位於哪個緩衝區,所佔住的塊的個數等
1.查詢buffer cache中不同物件佔住塊的個數(可以根據查詢將不經常訪問的大物件置於到recycle pool)
SELECT o.owner, object_name, object_type, COUNT(1) buffers --這個查詢獲得到經常訪問的物件,可以將其放到recycle pool中
FROM SYS.x$bh, dba_objects o
WHERE (tch = 1 OR (tch = 0 AND lru_flag < 8))
AND obj = o. object_id
AND o.owner NOT IN ('SYSTEM', 'SYS')
GROUP BY o.owner, object_name, object_type
ORDER BY buffers;
SELECT o.owner, object_name, object_type, COUNT(1) buffers --這個查詢獲得到經常訪問的物件,可以將其放到keep pool中
FROM SYS.x$bh, dba_objects o
WHERE tch > 10
AND lru_flag = 8
AND obj = o.object_id
AND o.owner NOT IN ('SYSTEM', 'SYS')
GROUP BY o.owner, object_name, object_type
ORDER BY buffers;
2.查詢單個物件佔住buffer cache中塊的總個數
SELECT COUNT(*)
FROM v$bh
WHERE objd=(
SELECT data_object_id
FROM Dba_Objects
WHERE object_name=UPPER('big_table')
AND owner='SCOTT'
AND status != 'free');
COUNT(*)
----------
4235
3.獲得所有不同的buffer pool 當前分配塊的總個數
SELECT NAME
,block_size
,SUM(buffers)
FROM v$buffer_pool
GROUP BY NAME,block_size
HAVING SUM(buffers)>0;
NAME BLOCK_SIZE SUM(BUFFERS)
---------- ---------- ------------
DEFAULT 8192 8958
KEEP 8192 1996
DEFAULT 16384 252
RECYCLE 8192 1996
4.獲得單個物件佔用buffer cache的比率
SELECT round(obj_cnt/totalcache_cnt*100,3)
FROM
(SELECT COUNT(*) AS obj_cnt
FROM v$bh
WHERE objd=(
SELECT data_object_id
FROM Dba_Objects
WHERE object_name=UPPER('big_table')
AND owner='SCOTT'))a,
(SELECT NAME
,block_size
,SUM(buffers) AS totalcache_cnt
,COUNT(*)
FROM v$buffer_pool
WHERE NAME='DEFAULT'
GROUP BY NAME,block_size
HAVING SUM(buffers)>0) b;
ROUND(OBJ_CNT/TOTALCACHE_CNT*100,3)
-----------------------------------
.015
七、查詢不同的buffer pool的命中率(buffer cache hit ratio)
低ratio並不能表明增加cache size可以提高效能。高ratio有時反而會讓你誤認為cache size已經足夠大而滿足要求了。比如:重複的掃描
一些大表或索引。然後大表的全表掃描往往都是物理讀,會人為的降低hit ratio。因此在不同高峰時段,多次採集資料非常有必要(或使用
StatsPack。
Db_cache_size 是針對預設的db_block_size的,對於非標準的block,要特別指定DB_nK_CACHE_SIZE 引數。
SELECT NAME,
block_size,
physical_reads,
db_block_gets,
consistent_gets,
(1 -(physical_reads / (DECODE(db_block_gets, 0, 1, db_block_gets) +
DECODE(consistent_gets, 0, 1, consistent_gets)))) * 100 "Hit Ratio"
FROM V$BUFFER_POOL_STATISTICS
ORDER BY NAME;
NAME BLOCK_SIZE PHYSICAL_READS DB_BLOCK_GETS CONSISTENT_GETS Hit Ratio
---------- ---------- -------------- ------------- --------------- ---------
DEFAULT 16384 63 5 128 52.632
DEFAULT 8192 21013 230479 879158 98.106
KEEP 8192 0 0 0 100.000
RECYCLE 8192 106 0 434 75.632
八、總結
儘管使用不同的緩衝池從某種程度上來說可以大大提高資料庫系統的I/O,給予了DBA更多的選擇性。然而,多個緩衝池(buffer pool)
增加了管理的複雜度,其次由於不同的緩衝池不能夠共享,在某種程度上來說,勢必造成buffer cache大小的浪費。因此,如果default
buffer pool能夠滿足現有的需求,儘可能的避免使用過多的緩衝池帶來管理的不便。
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/22578826/viewspace-703517/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- Buffer cache 的調整與優化(一)優化
- Linux工具效能調優系列二:buffer和cacheLinux
- buffer cache深度分析及效能調整(五)
- buffer cache深度分析及效能調整(六)
- buffer cache深度分析及效能調整(四)
- 讀書筆記-高階owi與oracle效能調整-cache buffer筆記Oracle
- oracle效能優化(二)-調整查詢Oracle優化
- 調整緩衝區快取記憶體(Buffer Cache)的效能(轉)快取記憶體
- 調整緩衝區快取記憶體(Buffer Cache)的效能(1)快取記憶體
- 調整緩衝區快取記憶體(Buffer Cache)的效能(2)快取記憶體
- 調整緩衝區快取記憶體(Buffer Cache)的效能(3)快取記憶體
- page cache與buffer cache的關係
- Nginx的優化調整方面Nginx優化
- buffer與cache的區別
- Buffer 與 Cache 的區別
- 技術分享 | 調整 max-write-buffer-size 優化 pika 效能10倍的案例優化
- 備份的優化和調整優化
- Oracle PL/SQL 優化與調整 -- Bulk 說明OracleSQL優化
- buffer 與cache 的區別2
- 共享池的調整與優化(Shared pool Tuning)優化
- Oracle Buffer Cache原理總結(二)Oracle
- linux cache與buffer的區別Linux
- swoole優化核心引數調整優化
- oracle效能優化-共享池調整Oracle優化
- oracle buffer cache管理機制_buffer cache dump與lru機制小記Oracle
- [書籍] Oracle Database 10g效能調整與優化OracleDatabase優化
- buffer cache與相關的latch等待事件事件
- 優化 MySQL: 3 個簡單的小調整優化MySql
- gc buffer busy的優化GC優化
- Buffer Cache 原理
- cache buffer chainAI
- 記憶體中,cache與buffer的含義記憶體
- Oracle調優---調整優化器行為的一般性原則Oracle優化
- 一次效能優化調整過程.優化
- SQL調整優化與10053跟蹤分析一例SQL優化
- TiDB 查詢優化及調優系列(四)查詢執行計劃的調整及優化原理TiDB優化
- IO之核心buffer----"buffer cache"
- Nginx安全優化與效能調優Nginx優化