Oracle有效地使用块(2)

Extents

  An extent is a logical unit of database storage space allocation consisting of a number of contiguous data blocks. One or more extents make up a segment. When the existing space in a segment is completely used, the Oracle server allocates a new extent for the segment

Advantages of Large Extents

  • Large extents avoid dynamic extent allocation, because segments with larger extents are less likely to need to be extended
  • Larger extents can have a small performance benefit because the Oracle server can read one large extent from disk with fewer multi-block reads than would be required to read many small extents.By matching extent sizes to the I/O and space allocation sizes, the performance cost of having many extents in a segment is minimized. However,for a table that never has a full table scan operation, it makes no difference in terms of query performance whether the table has one extent or multiple extents.

  • Extent maps list all the extents for a certain segment. When MAXEXTENTSis set to UNLIMITED, these maps are in multiple blocks. For best performance, you should be able to read the extent map with a single I/O. Performance degradesif multiple I/Os are necessary for a full table scan to get the extent map. Also, a large number of extents can degrade data dictionary performance, becauseeach extent uses space in the dictionary cache. 

Disadvantages of Large Extents

  • Large extents require more contiguous blocks, therefore the Oracle server may have difficulty finding enough contiguous space to store them.
  • The DBA sizes the segment to allow for growth, so some ofthe space allocated to the segment will not be used initially.

测试 db_file_multiblock_read_coun 与 extent 对IO影响 :

1.db_file_multiblock_read_coun=16 extent=128(最大值)

 1 SQL> create table t as select * from dba_objects;
 2 
 3 Table created.
 4 
 5 SQL> insert into t select * from t;
 6 
 7 128607 rows created.
 8 
 9 SQL> commit;
10 
11 Commit complete.
12 
13 SQL> 
14 
15 
16 SQL> select file_id,extent_id,block_id,blocks from dba_extents
17   2  where owner='SYS' and segment_name='T';
18 --file_id文件中extent所包含block的数量
19    FILE_ID  EXTENT_ID   BLOCK_ID     BLOCKS
20 ---------- ---------- ---------- ----------
21          1          0     135977          8
22          1          1     135985          8
23          1          2     135993          8
24          1          3     136001          8
25          1          4     136009          8
26          1          5     136017          8
27          1          6     136025          8
28          1          7     136033          8
29          1          8     136041          8
30          1          9     136049          8
31          1         10     136057          8
32 
33    FILE_ID  EXTENT_ID   BLOCK_ID     BLOCKS
34 ---------- ---------- ---------- ----------
35          1         11     136065          8
36          1         12     137609          8
37          1         13     137617          8
38          1         14     137625          8
39          1         15     137633          8
40          1         16     137737        128
41          1         17     137865        128
42          1         18     137993        128
43          1         19     138121        128
44          1         20     138249        128
45          1         21     138377        128
46 
47    FILE_ID  EXTENT_ID   BLOCK_ID     BLOCKS
48 ---------- ---------- ---------- ----------
49          1         22     138505        128
50          1         23     138633        128
51          1         24     138761        128
52          1         25     138889        128
53          1         26     139017        128
54          1         27     139145        128
55          1         28     139273        128
56          1         29     139401        128
57          1         30     139529        128
58          1         31     139657        128
59          1         32     139785        128
60 
61    FILE_ID  EXTENT_ID   BLOCK_ID     BLOCKS
62 ---------- ---------- ---------- ----------
63          1         33     139913        128
64          1         34     140041        128
65          1         35     140169        128
66          1         36     140297        128
67          1         37     140425        128
68          1         38     140553        128
69          1         39     140681        128
70          1         40     140809        128
71          1         41     140937        128
72          1         42     141065        128
73          1         43     141193        128
74 
75    FILE_ID  EXTENT_ID   BLOCK_ID     BLOCKS
76 ---------- ---------- ---------- ----------
77          1         44     141321        128
78          1         45     141449        128
注:自己手动创建表空间时,extent的大小最好统一(uniform size)

--手动设置db_file_multiblock_read_count值

1 SQL> alter session set db_file_multiblock_read_count=16;
2 --每次读取16个块
3 --The maximum value is the operating system's maximum I/O size expressed as Oracle blocks ((max I/O size)/DB_BLOCK_SIZE). 
4 --If you set this parameter to a value greater than the maximum, Oracle uses the maximum.

--查看测试结果

 1 SQL> ALTER SESSION SET EVENTS '10046 TRACE NAME CONTEXT FOREVER,LEVEL 12';
 2 
 3 Session altered.
 4 
 5 SQL> select count(*) from t;
 6 
 7   COUNT(*)
 8 ----------
 9     257214
10 
11 SQL> @$ORACLE_HOME/trace.sql
12 
13 TRACE_FILE_NAME
14 --------------------------------------------------------------------------------
15 /opt/oracle/diag/rdbms/nwom/nwom/trace/nwom_ora_3435.trc
16 
17 SQL> !more /opt/oracle/diag/rdbms/nwom/nwom/trace/nwom_ora_3435.trc
18 PARSING IN CURSOR #47971673691112 len=22 dep=0 uid=0 oct=3 lid=0 tim=1361937403231126 hv=2763161912 ad='cb85fc18' sqlid='cyzznbykb509s'
19 select count(*) from t
20 END OF STMT
21 PARSE #47971673691112:c=10999,e=17498,p=332,cr=73,cu=0,mis=1,r=0,dep=0,og=1,plh=2966233522,tim=1361937403231125
22 EXEC #47971673691112:c=0,e=33,p=0,cr=0,cu=0,mis=0,r=0,dep=0,og=1,plh=2966233522,tim=1361937403231214
23 WAIT #47971673691112: nam='SQL*Net message to client' ela= 3 driver id=1650815232 #bytes=1 p3=0 obj#=-1 tim=1361937403231247
24 WAIT #47971673691112: nam='direct path read' ela= 46 file number=1 first dba=135978 block cnt=6 obj#=254332 tim=1361937403231560
25 .......
26 WAIT #47971673691112: nam='direct path read' ela= 117 file number=1 first dba=136032 block cnt=16 obj#=254332 tim=1361937403232361
27 WAIT #47971673691112: nam='direct path read' ela= 65 file number=1 first dba=136048 block cnt=16 obj#=254332 tim=1361937403232577
28 WAIT #47971673691112: nam='direct path read' ela= 40 file number=1 first dba=136064 block cnt=9 obj#=254332 tim=1361937403232743
29 WAIT #47971673691112: nam='direct path read' ela= 31 file number=1 first dba=137609 block cnt=7 obj#=254332
30 ........
31 file number:文件号
32 first dba:数据块block_id
33 block cnt: 一次读取数据块的数量
34 
35 上述测试 一次读block数最大为16。此时参数db_file_multiblock_read_count=16;一个extent包含block最多为128

2.db_file_multiblock_read_count=512  extent=128(最大值)

--改变db_file_multiblock_read_count大小

 1 SQL> alter session set db_file_multiblock_read_count=512;   
 2 
 3 Session altered.
 4 
 5 SQL> ALTER SESSION SET EVENTS '10046 TRACE NAME CONTEXT FOREVER,LEVEL 12';
 6 
 7 Session altered.
 8 
 9 SQL> select count(*) from t01;  
10 
11   COUNT(*)
12 ----------
13     385821
14 
15 SQL> @$ORACLE_HOME/trace.sql
16 
17 TRACE_FILE_NAME
18 --------------------------------------------------------------------------------
19 /opt/oracle/diag/rdbms/nwom/nwom/trace/nwom_ora_6783.trc
20 
21 SQL>!more  /opt/oracle/diag/rdbms/nwom/nwom/trace/nwom_ora_6783.trc
22 
23 --查看trace日志
24 PARSING IN CURSOR #47004310211592 len=24 dep=0 uid=0 oct=3 lid=0 tim=1361954062660602 hv=4036868481 ad='cb5e8510' sqlid='f9ny9vbs9vfc1'
25 select count(*) from t01
26 END OF STMT
27 PARSE #47004310211592:c=11997,e=11414,p=192,cr=88,cu=0,mis=1,r=0,dep=0,og=1,plh=705462345,tim=1361954062660600
28 EXEC #47004310211592:c=0,e=23,p=0,cr=0,cu=0,mis=0,r=0,dep=0,og=1,plh=705462345,tim=1361954062660688
29 WAIT #47004310211592: nam='SQL*Net message to client' ela= 3 driver id=1650815232 #bytes=1 p3=0 obj#=-1 tim=1361954062660719
30 WAIT #47004310211592: nam='db file scattered read' ela= 131 file#=1 block#=137642 blocks=7 obj#=254343 tim=1361954062661029
31 WAIT #47004310211592: nam='db file scattered read' ela= 157 file#=1 block#=137649 blocks=8 obj#=254343 tim=1361954062661322
32 ......
33 WAIT #47004310211592: nam='db file scattered read' ela= 762 file#=1 block#=143197 blocks=44 obj#=254343 tim=1361954062710267
34 WAIT #47004310211592: nam='db file scattered read' ela= 2364 file#=1 block#=143241 blocks=128 obj#=254343 tim=1361954062713521
35 WAIT #47004310211592: nam='db file scattered read' ela= 2130 file#=1 block#=143369 blocks=128 obj#=254343 tim=1361954062717127
36 ......
37 
38 file number:文件号
39 first dba:数据块block_id
40 block cnt: 一次读取数据块的数量
41 
42 测试 一次读block数最大为128。此时参数db_file_multiblock_read_count=512;一个extent包含block最多为128。通过两次测试得出ora的物理IO最大取决于db_file_multiblock_read_count与extent中的最小值

推论:在OS最大IO(通常为1M,可以通过dd自行测试)范围内,db的IO最大不会超过extent的值。

原文地址:https://www.cnblogs.com/polestar/p/2936490.html