DBMS_STATS
The DBMS_STATS package was introduced in Oracle 8i and is Oracles preferred method of gathering object statistics. Oracle list a number of benefits to using it including parallel execution, long term storage of statistics and transfer of statistics between servers. Once again, it follows a similar format to the other methods: EXEC DBMS_STATS.gather_database_stats;
EXEC DBMS_STATS.gather_database_stats(estimate_percent => 15); EXEC DBMS_STATS.gather_schema_stats('SCOTT');
EXEC DBMS_STATS.gather_schema_stats('SCOTT', estimate_percent => 15); EXEC DBMS_STATS.gather_table_stats('SCOTT', 'EMPLOYEES');
EXEC DBMS_STATS.gather_table_stats('SCOTT', 'EMPLOYEES', estimate_percent => 15); EXEC DBMS_STATS.gather_index_stats('SCOTT', 'EMPLOYEES_PK');
EXEC DBMS_STATS.gather_index_stats('SCOTT', 'EMPLOYEES_PK', estimate_percent => 15); This package also gives you the ability to delete statistics: EXEC DBMS_STATS.delete_database_stats;
EXEC DBMS_STATS.delete_schema_stats('SCOTT'); EXEC DBMS_STATS.delete_table_stats('SCOTT', 'EMPLOYEES'); EXEC DBMS_STATS.delete_index_stats('SCOTT', 'EMPLOYEES_PK'); --------------------------------------------------------------------------------------
自從Oracle8.1.5引入dbms_stats包,Experts們便推薦使用dbms_stats取代analyze。 理由如下
dbms_stats可以并行分析
dbms_stats有自動分析的功能(alter table monitor ) analyze 分析統(tǒng)計信息的不準確some times 1,2好理解,且第2點實際上在VLDB中是最吸引人的;3以前比較模糊,看了metalink236935.1 解釋,analyze在分析Partition表的時候,有時候會計算出不準確的Global statistics . 原因是,dbms_stats會實在的去分析表全局統(tǒng)計信息(當指定參數(shù));而analyze是將表分區(qū)(局部)的statistics 匯總計算成表全局statistics ,可能導致誤差。
如果想分析整個用戶或數(shù)據(jù)庫,還可以采用工具包,可以并行分析
Dbms_utility(8i以前的工具包) Dbms_stats(8i以后提供的工具包) 如 dbms_stats.gather_schema_stats(User,estimate_percent=>100,cascade=> TRUE); dbms_stats.gather_table_stats(User,TableName,degree => 4,cascade => true); 這是對命令與工具包的一些總結(jié)
1、對于分區(qū)表,建議使用DBMS_STATS,而不是使用Analyze語句。
a) 可以并行進行,對多個用戶,多個Table b) 可以得到整個分區(qū)表的數(shù)據(jù)和單個分區(qū)的數(shù)據(jù)。 c) 可以在不同級別上Compute Statistics:單個分區(qū),子分區(qū),全表,所有分區(qū) d) 可以倒出統(tǒng)計信息 e) 可以用戶自動收集統(tǒng)計信息 2、DBMS_STATS的缺點
a) 不能Validate Structure b) 不能收集CHAINED ROWS, 不能收集CLUSTER TABLE的信息,這兩個仍舊需要使用Analyze語句。 c) DBMS_STATS 默認不對索引進行Analyze,因為默認Cascade是False,需要手工指定為True 3、對于oracle 9里面的External Table,Analyze不能使用,只能使用DBMS_STATS來收集信息。
-----------------------------------------------------------------
10G的文檔是這么說的: Do not use the COMPUTE and ESTIMATE clauses of ANALYZE to collect optimizer statistics. These clauses are supported for backward compatibility. Instead, use the DBMS_STATS package, which lets you collect statistics in parallel, collect global statistics for partitioned objects, and fine tune your statistics collection in other ways. The cost-based optimizer, which depends upon statistics, will eventually use only statistics that have been collected by DBMS_STATS analyze的功能已經(jīng)明確:
Use the ANALYZE statement (rather than DBMS_STATS) forstatistics collection not related to the cost-based optimizer: To use the VALIDATE or LIST CHAINED ROWS clauses
To collect information on freelist blocks
在收集與CBO優(yōu)化器不相關(guān)的統(tǒng)計信息的時候ANALYZE語句要優(yōu)于DBMS_STATS包
-----------------------------------
EX: begin for owner in (select username from dba_users where username not in ('SYS','SYSTEM')) loop dbms_output.disable; dbms_output.enable(1000000); dbms_output.put_line('Schema: '||owner.username); select sysdate into start_time from dual; dbms_output.put_line('Analyze start from : '||start_time); dbms_stats.gather_schema_stats(ownname => owner.username, estimate_percent => 20, block_sample=> true, cascade=>true); select sysdate into end_time from dual; dbms_output.put_line('Analyze complete at : '||end_time); dbms_output.put_line('---------------------------'); end loop; dbms_stats.gather_table_stats(ownname =>, tabname =>, partname =>, estimate_percent =>, block_sample =>, method_opt =>, degree =>,parallel degree(并行收集維度) 看CPU個數(shù) granularity =>, cascade =>,true is also gather columns and index’s statistics; no_invalidate =>); ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
當索引整個塊成為空塊的時候,會被放置于freelist上,可以被重用。但是重用前結(jié)構(gòu)上還是臨時放置于B-Tree中。
這時analyze & dbms_stats在分析時會有不同,analyze會將這些空的block計算為leaf block,而dbms_stats不將其計算在內(nèi)。
請看例子
1 create table test
2 as 3 select rownum x 4* from dba_objects SQL> / Table created.
SQL> select count(*) from test;
COUNT(*)
———- 6114 1 create index test_idx on test(x)
2* pctfree 95 SQL> / Index created.
SQL> analyze table test compute statistics;
Table analyzed.
SQL> select index_name,blevel,leaf_blocks,distinct_keys,num_rows,last_analyzed from dba_indexes where index_name=’TEST_IDX’ and owner=’SYS’;
INDEX_NAME BLEVEL LEAF_BLOCKS DISTINCT_KEYS NUM_ROWS LAST_ANALYZED
—————————— ———- ———– ————- ———- —————– TEST_IDX 1 408 6114 6114 20060513 01:00:25 SQL> delete from test where x<3000;
2999 rows deleted.
SQL> commit;
Commit complete.
SQL> analyze index test_idx compute statistics;
Index analyzed.
SQL> select index_name,blevel,leaf_blocks,distinct_keys,num_rows,last_analyzed
2 from dba_indexes where index_name=’TEST_IDX’ and owner=’SYS’; INDEX_NAME BLEVEL LEAF_BLOCKS DISTINCT_KEYS NUM_ROWS LAST_ANALYZED
—————————— ———- ———– ————- ———- —————– TEST_IDX 1 408 3115 3115 20060513 01:03:31 SQL> exec DBMS_STATS.GATHER_INDEX_STATS(’SYS’,'TEST_IDX’);
PL/SQL procedure successfully completed.
SQL> select index_name,blevel,leaf_blocks,distinct_keys,num_rows,last_analyzed
2 from dba_indexes where index_name=’TEST_IDX’ and owner=’SYS’; INDEX_NAME BLEVEL LEAF_BLOCKS DISTINCT_KEYS NUM_ROWS LAST_ANALYZED
—————————— ———- ———– ————- ———- —————– TEST_IDX 1 209 3115 3115 20060513 01:04:28 FROM:http://www./blog/?p=21
////////////////////////////////////////////////////////////////////////////////////////////////////////////
我們知道從oracle8i開始﹐analyze語句和dbms_stats包都可以收集相關(guān)對象(Tables﹑Indexes﹑Clusters and Materialized Views)的statistics。那哪些statistics的收集應該使用analyze語句﹐哪些statistics的收集應該使用dbms_stats包呢﹖
對于使用哪個去收集statistics﹐應該把一個原則﹐凡是與cost-based optimizer相關(guān)的statistics﹐都應通過dbms_stats包收集。與cost-based optimizer無關(guān)的statistics(如empty blocks﹐average space等)都應通過analyze語句去收集。
之所以要用dbms_stats包去替代analyze收集優(yōu)化器statistics﹐是因為dbms_stats包能收集并行statistics和分區(qū)對象的全局statistics。
當然analyze語句在其它方面的statistics收集﹐是dbms_stats所無法取代的﹐如﹕
1. 收集在freelist上的blocks信息
2. 檢驗存儲格式的合法性
analyze table bk_test_t validate structure cascade online;
3. 識別表或cluster的行遷移與行鏈接
為了能使用analyze….list chained rows語句識別行遷移與行鏈接﹐必須先在執(zhí)行analyze語句所在的schema內(nèi)執(zhí)行$ORACLE_HOME/rdbms/admin/utlchain.sql(或utlchn1.sql)腳本建立chained_rows表。在chained_rows建立之后﹐就可以執(zhí)行下面的語句﹕
analyze table bk_test list chained rows into chained_rows;
from:http://space./?uid-33600-action-viewspace-itemid-266418
本文來自CSDN博客,轉(zhuǎn)載請標明出處:http://blog.csdn.net/aicon/archive/2010/04/12/5474240.aspx |
|
來自: 舞·戀上您的舞 > 《SQL調(diào)優(yōu)》