相关链接
- 【官】142 DBMS_STATS
- 1.Excel目录
- 2.如何找到Oralce存储过程——官方文档
- 3. Oracle执行计划之2_统计信息(Statistic)
- 4. 142-10 SYS.DBMS_STATS.delete_column_stats
- 5. 142-12 SYS.DBMS_STATS.delete_database_stats
- 6. 142-15 SYS.DBMS_STATS.delete_index_stats
- 7. 142-18 SYS.DBMS_STATS.delete_schema_stats
- 8. 142-21 SYS.DBMS_STATS.delete_table_stats
- 9. 142-39 SYS.DBMS_STATS.gather_database_stats
- 10. 142-42 SYS.DBMS_STATS.gather_index_stats
- 11. 142-43 SYS.DBMS_STATS.gather_schema_stats
- 12. 142-45 SYS.DBMS_STATS.gather_table_stats
- 13. 142-87 SYS.DBMS_STATS.set_column_stats
- 14. 142-90 SYS.DBMS_STATS.set_index_stats
- 15. 142-95 SYS.DBMS_STATS.set_table_stats
一、统计信息(Statistic)
统计信息主要是描述数据库中表,索引的大小,规模,数据分布状况等的一类信息。例如,表的行数,块数,平均每行的大小,索引的 leaf blocks,索引字段的行数,不同值的大小等,都属于统计信息。
根据这些统计信息, optimizer (优化器)可以选择更好的执行计划。从 Oracle11G 开始,数据库统计信息的自动收集被整合到自动维护任务中,基本上都是默认自动执行的,也满足大多数情形下的运行需求,不过也可以手动收集。
- 使用 gather_stats_job 自动收集是在创建数据库时自动创建的,并由调度程序进行管理。他会收集数据库中优化程序统计信息缺失或已过时的所有对象的统计信息。
- 使用
dbms_stats
程序包手动收集收集的是系统统计信息。主要提供了搜集(gather),删除(delete),导出(export),导入(import),修改(set)统计信息的方法。说起 dbms_stats 那就有必要说说analyze 命令。 dbms_stats
与analyze
的区别:dbms_stats 是 Oracle9i 及后续版本中用于收集统计信息的包,虽然 analyze 命令也一直可以使用,但是现在已经不推荐使用 analyze 命令来收集统计信息,而是使用 dbms_stats。两者之间有很大的不同,dbms_stats 能正确收集分区表的统计信息,也就是说能够收集 global statistic,而 analyze 只能收集最低层次对象的统计信息,然后推导和汇总出高一级对象的统计信息,如果分区表只会收集分区统计信息,然后再汇总出所有分区的统计信息,得到表一级的统计信息。- 建议使用
DBMS_STATS
,Analyze
基本不用了。 - 听说还有DBMS_DDL、DBMS_UTILITY也可以收集某些统计信息,但没有深入研究。
二、统计信息内容
统计信息存储位置(不完统计)
表的统计信息:
包含表行数,使用的块数,空的块数,块的使用率,行迁移和链接的数量,pctfree,pctused的数据,行的平均大小
索引列的统计信息:
包含索引的深度(B-Tree的级别),索引叶级的块数量,集群因子(clustering_factor), 唯一值的个数。
列的统计信息 :
包含 唯一的值个数,列最大小值,密度(选择率),数据分布(直方图信息),NUll值个数
搜集的统计信息同时存储在以下三种视图下:【DBA_】 【ALL_】【USER_】
- Analyze统计信息:
Type 种类 | Description 描述 | SourceView 来源视图 | Seri 序号 | SourceColumn 来源列( * 是精确计算值) | |
---|---|---|---|---|---|
1 | 表统计信息 table statistics | Number of rows 行数量(数据条数)。 | ALL_TABLES | 20 | NUM_ROWS |
2 | Number of data blocks below the High Water Mark1 (历史最)高水位(High Water Mark) 标记数据块的数量 BLOCKS + EMPTY_BLOCKS +1 = DBA_SEGMENTS.BLOCKS 这里有一个数据库块被保留用作segment header。 | ALL_TABLES | 21 | *BLOCKS | |
3 | Number of data blocks allocated to the table that have never been used 已分配给表但给从未使用过的数据块数。 BLOCKS + EMPTY_BLOCKS +1 = DBA_SEGMENTS.BLOCKS 这里有一个数据库块被保留用作segment header。 | ALL_TABLES | 22 | *EMPTY_BLOCKS | |
4 | Average available free space in each data block in bytes 每个数据块的平均可用空闲空间(单位:字节)。 | ALL_TABLES | 23 | AVG_SPACE | |
5 | Number of chained rows 表中行连接和行迁移的数量。 | ALL_TABLES | 24 | CHAIN_CNT | |
6 | Average row length, including the row Overhead2, in bytes 平均行长度,包括 块开销(Overhead)(单位:字节)。 | ALL_TABLES | 25 | AVG_ROW_LEN | |
1 | 索引统计信息 index statistics | Depth Of The Index3 from its Root Block4 to its Leaf Blocks5. B-Tree索引中从 根块(root block) 到 叶块(left block) 的 索引深度(Depth of the index) (纵向IO次数)。 | ALL_INDEXES | 24 | *BLEVEL |
2 | Number of leaf blocks. 叶块(leaf blocks)数量。 | ALL_INDEXES | 25 | LEAF_BLOCKS | |
3 | Number of distinct index values 不同索引值的个数。 | ALL_INDEXES | 26 | DISTINCT_KEYS 索引DISTINCT后个数 | |
4 | Average number of leaf blocks for each index value 每个索引值(用于表上的索引)的平均数据块数。 | ALL_INDEXES | 27 | AVG_LEAF_BLOCKS_PER_KEY = LEAF_BLOCKS / DISTINCT_KEYS = 25 / 26 | |
5 | Average number of data blocks for each index value (for an index on a table) 集群因子(索引值的行有序程度)。 | ALL_INDEXES | 28 | AVG_DATA_BLOCKS_PER_KEY 单个索引引用的平均数据块数 = CLUSTERING_FACTOR / DISTINCT_KEYS = 29 / 26 | |
6 | Clustering Factor6 (how well ordered the rows are about the indexed values) 集群因子(索引值的行有序程度)。 | ALL_INDEXES | 29 | CLUSTERING_FACTOR row存储的越有序,clustering factor的值越低 | |
1 | 簇(集群)统计信息 cluster statistics | Number of blocks in the table divided by number of Cluster Key7. 表中块的数量除以 簇键(Cluster Key) 的数量 创建簇的参数SIZE,决定了每个簇键值可以关联多少字节的数据,进而计算出每个数据块能容纳多少个簇键。 当SIZE设置过高,单独的数据块可以容纳的簇键会减少,且对于单个簇键会占用比实际需求更多的空间,造成空间的浪费。 当SIZE设置过低,单个的簇键无法在单独的数据块中容纳一条完整的数据,进而导致溢出数据部分串联至新块,影响聚合度。 当SIZE设置为1024时,对于一个8K(8192)的标准块,由于数据块的pct_free,实际可容纳7个簇键。 | ALL_CLUSTERS | 16 | AVG_BLOCKS_PER_KEY = 表中块的数量 / 簇键的数量 |
1 | 系统统计信息 system statistics | i/o performance and utilization io性能和利用率 | - | - | 在他人文章中看到 |
2 | cpu performance and utilization cpu性能和利用率 | - | - | 但在Analyze官方文档中未找到相关描述 |
- 其他统计信息
Type 种类 | Description 英文描述 | Translation 中文描述 | StoreView 存储视图 | Seri 序号 | StoreColumn 存储列( * 是精确计算值) |
---|---|---|---|---|---|
列统计信息 column statistics | number of distinct values (ndv) in column | 列中distinct的值 | ALL_TAB_COLUMNS | 14 | NUM_DISTINCT |
number of nulls in column | 列中null的值 | ALL_TAB_COLUMNS | 18 | NUM_NULLS | |
data distribution (histogram) | 数据分布 | ALL_TAB_COLUMNS | 15 | LOW_VALUE 列上最小值 | |
ALL_TAB_COLUMNS | 16 | HIGH_VALUE 列上最大值 | |||
ALL_TAB_COLUMNS | 17 | DENSITY 密度 | |||
ALL_TAB_COLUMNS | 19 | NUM_BUCKETS 桶数 | |||
ALL_TAB_COLUMNS | 26 | AVG_COL_LEN 列平均字节长度 | |||
ALL_TAB_COLUMNS | 31 | HISTOGRAM 直方图类型 | |||
系统统计信息 system statistics | i/o performance and utilization | io性能和利用率 | |||
cpu performance and utilization | cpu的性能和利用率 |
20/09/14
M
High Water Mark :HWM(High Water Mark) 是一个标记,用来说明已经有多少没有使用的数据块分配给这个segment。HWM通常增长的幅度为一次5个数据块,原则上HWM只会增大,不会缩小,即使将表中的数据全部删除,HWM还是为原值,由于这个特点,使HWM很象一个水库的历史最高水位,这也就是HWM的原始含义,当然不能说一个水库没水了,就说该水库的历史最高水位为0。但是如果我们在表上使用了truncate命令,则该表的HWM会被重新置为0。
BLOCKS 列代表该表中曾经使用过得数据库块的数目,即水线。
EMPTY_BLOCKS 代表分配给该表,但是在水线以上的数据库块,即从来没有使用的数据块。 ↩︎Overhead :块开销(Overhead),Oracle使用块开销(Overhead)来管理数据块自身。块开销不用于存储用户数据。 ↩︎
Depth Of The Index :索引深度(Depth Of The Index) ,如下图所示为一个 3 阶的 B-Tree:,每次查询数据需要3次磁盘I/O操作,和3次内存查找操作。
图片来自 ↩︎Root Block :根块(Root Blocks),B-Tree设计模仿植物的根茎叶关系,详见left block。 ↩︎
Leaf Blocks :叶子块(Leaf Blocks) ,Oracle 数据库使用 B-trees 存储索引,来加速数据访问。索引中的数据块,其树形结构分为三层:root block 根块、branch block 枝块、leaf block 叶块。其中枝节点用来检索,可以有多层(层数取决于数据量)。叶块特点为:①最低级别的索引块、②leaf block包含索引列和指向表中每个匹配行的ROWID值、③对于唯一索引, 每个rowid指向对应唯一地址。非唯一索引,按索引键和 rowid 排序、④由于平衡扩张特点,所有叶子节点索引深度相同、⑤双向链表:整个叶子节点部分是一个双向链表、⑥系统从磁盘读取数据到内存时是以磁盘块(block)为基本单位的,位于同一个磁盘块中的数据会被一次性读取出来。 ↩︎
Clustering factor :集群因子(Clustering Factor ),表示 熵-混乱程度,该值越低,表示存储的索引键的存储越有序。
Clustering Factor的计算方式如下:
(1)、扫描一个索引(large index range scan);
(2)、比较某行的rowid和前一行的rowid,如果这两个rowid不属于同一个数据块,那么cluster factor增加1;
(3)、整个索引扫描完毕后,就得到了该索引的clustering factor。
如果clustering factor接近于表存储的块数,说明这张表是按照索引字段的顺序存储的。
如果clustering factor接近于行的数量,那说明这张表不是按索引字段顺序存储的。
在计算索引访问成本的时候,这个值十分有用。Clustering Factor乘以选择性参数(selectivity)就是访问索引的开销。
如果这个统计数据不能真实反映出索引的真实情况,那么可能会造成优化器错误的选择执行计划。另外如果某张表上的大多数访问是按照某个索引做索引扫描,那么将该表的数据按照索引字段的顺序重新组织,可以提高该表的访问性能。 ↩︎Cluster Key :簇键(Cluster Key),在1个簇表(Cluster Table)内,簇键(Cluster Key) 是指各簇键列(Cluster Key Column)的值。1个簇内有多个簇表(Cluster Table),簇表(Cluster Table)内各个数据行使用相同的簇键列(Cluster Key Column),在簇表(Cluster Table)及索引表簇(Cluster Index)中只会被存储1次。因此与非簇表(Nonclustered Table)相比,簇表(Cluster Table)存储表和表数据所需的空间会减少。每个簇键(Cluster Key) 的值只会存储1次,簇表(Cluster Table)中相关表所包含的相同簇键值的数据共享同1个簇键(Cluster Key)。 ↩︎