| Oracle Database パフォーマンス・チューニング・ガイド 10gリリース2(10.2) B19207-02 |
|
この章では、問合せオプティマイザにとって統計が重要である理由、およびDBMS_STATSパッケージを使用したオプティマイザ統計の収集方法と使用方法を説明します。
この章には次の項があります。
オプティマイザ統計は、データベースとそのオブジェクトに関する詳細情報を記述するデータの集合です。これらの統計は、問合せオプティマイザで各SQL文に最適の実行計画を選択するために使用されます。オプティマイザ統計には次のものがあります。
オプティマイザ統計はデータ・ディクショナリに格納されます。また、データ・ディクショナリ・ビューを使用して表示できます。「統計の参照」を参照してください。
データベース内のオブジェクトは常に変化するため、これらのデータベース・オブジェクトが正確に記述されるように統計を定期的に更新する必要があります。統計はOracleにより自動的にメンテナンスされます。また、DBMS_STATSパッケージを使用するとオプティマイザ統計を手動でメンテナンスできます。自動プロセスと手動プロセスについては、「自動統計収集」または「手動統計収集」を参照してください。
DBMS_STATSパッケージにも、統計を管理するためのプロシージャが用意されています。統計のコピーを保存してリストアできます。あるシステムから統計をエクスポートし、別のシステムにインポートできます。たとえば、本番システムからテスト・システムに統計をエクスポートできます。また、統計が変更されないようにロックすることも可能です。ロック方法については、「表統計またはスキーマ統計のロック」を参照してください。
推奨の統計収集方法は、Oracleで統計の自動収集を可能にすることです。Oracleでは、すべてのデータベース・オブジェクトの統計が自動的に収集され、定期的にスケジュールされたメンテナンス・ジョブで統計がメンテナンスされます。自動化された統計収集により、問合せオプティマイザの管理に関連する多数の手動タスクが不要になり、統計の欠落または失効が原因で不適切な実行計画が生成される可能性が大幅に低下します。
オプティマイザ統計は、GATHER_STATS_JOBジョブで自動的に収集されます。このジョブでは、データベース内で次の統計を持つすべてのオブジェクトの統計が収集されます。
このジョブはデータベースの作成時に自動的に作成され、スケジューラにより管理されます。このスケジューラでは、メンテナンス・ウィンドウがオープンすると、このジョブが実行されます。デフォルトでは、メンテナンス・ウィンドウは、毎晩午後10時〜午前6時まで、また週末は1日中オープンしています。
stop_on_window_close属性は、メンテナンス・ウィンドウがクローズしたとき、GATHER_STATS_JOBを続けるかどうかを制御します。stop_on_window_close属性のデフォルト設定は、TRUEであり、スケジューラはメンテナンス・ウィンドウがクローズしたときGATHER_STATS_JOBを終了します。残りのオブジェクトは、その後、次のメンテナンス・ウィンドウで処理されます。
GATHER_STATS_JOBジョブでは、DBMS_STATS.GATHER_DATABASE_STATS_JOB_PROCプロシージャがコールされ、オプティマイザ統計が収集されます。GATHER_DATABASE_STATS_JOB_PROCプロシージャによりデータベース・オブジェクトの統計が収集されるのは、オブジェクトの統計が以前に収集されていない場合、または基礎となるオブジェクトが大幅に(行の10%以上が)変更されたために既存の統計が失効している場合です。DBMS_STATS.GATHER_DATABASE_STATS_JOB_PROCは内部プロシージャですが、その動作はGATHER AUTOオプションを使用するDBMS_STATS.GATHER_DATABASE_STATSプロシージャとほとんど同じです。主な違いは、DBMS_STATS.GATHER_DATABASE_STATS_JOB_PROCプロシージャでは、統計を必要とするデータベース・オブジェクトに優先順位が設定されるため、更新済の統計を最も必要とするオブジェクトが最初に処理されることです。これにより、メンテナンス・ウィンドウがクローズする前に、最も必要性の高い統計が確実に収集されます。
自動統計収集は、データベースの作成時または以前のリリースからのアップグレード時にデフォルトで使用可能になります。DBA_SCHEDULER_JOBSビューを表示すると、ジョブの存在を確認できます。
SELECT * FROM DBA_SCHEDULER_JOBS WHERE JOB_NAME = 'GATHER_STATS_JOB';
自動統計収集を使用禁止にする場合に最も直接的なアプローチは、次のようにGATHER_STATS_JOBを使用禁止にすることです。
BEGIN DBMS_SCHEDULER.DISABLE('GATHER_STATS_JOB'); END; /
自動統計収集は、「失効している統計の判別」で説明するように変更監視機能に依存します。この機能が無効になっている場合、自動統計収集ジョブでは失効している統計を検出できません。この機能は、STATISTICS_LEVELパラメータがTYPICALまたはALLに設定されている場合に有効になります。デフォルト値はTYPICALです。
この項では、次の内容を説明します。
普通の速度で変更されるほとんどのデータベース・オブジェクトの場合は、自動統計収集で十分です。ただし、自動統計収集では不十分な場合があります。自動統計収集は夜間のバッチ・ウィンドウで実行されるため、日中に大幅に変更された表の統計が失効している可能性があります。通常、この種のオブジェクトには次の2つのタイプがあります。
揮発性の高い表の場合は、次の2つのアプローチがあります。
OPTIMIZER_DYNAMIC_SAMPLINGパラメータにより制御されます。このパラメータは2以上の値に設定する必要があります。デフォルト値は2です。統計は、削除してからロックすることでNULLに設定できます。
BEGIN DBMS_STATS.DELETE_TABLE_STATS('OE','ORDERS'); DBMS_STATS.LOCK_TABLE_STATS('OE','ORDERS'); END; /
設定できるサンプリング・レベルの詳細は、「動的サンプリング・レベル」を参照してください。
この方法はGATHER_STATS_JOBよりも効率的です。これは、夜間のバッチ・ウィンドウで表に関して生成された統計が、日中のワークロードに関して最も適切な統計であるとはかぎらないためです。
バルク・ロード対象の表の場合は、統計収集プロシージャをロード・プロセスの直後に、可能であればバルク・ロードを実行するのと同じスクリプトまたはジョブの一部として、実行する必要があります。
外部表の場合、GATHER_SCHEMA_STATS、GATHER_DATABASE_STATSおよび自動統計収集処理中には統計は収集されません。ただし、GATHER_TABLE_STATSを使用すると外部表の統計を個別に収集できます。外部表のサンプリングはサポートされていないため、ESTIMATE_PERCENTオプションは明示的にNULLに設定する必要があります。外部表のデータ操作は許可されないため、対応するファイルに変更があったときに外部表を分析すれば十分です。
STATISTICS_LEVELをBASICに設定して監視機能を無効にすると、自動統計収集では失効している統計を検出できません。この場合は、統計を手動で収集する必要があります。自動監視機能の詳細は、「失効している統計の判別」を参照してください。
システム統計も、手動で収集する必要があります。この種の統計は自動的には収集されません。 詳細は、「システム統計」を参照してください。
動的パフォーマンス表など、固定オブジェクトの統計は、GATHER_FIXED_OBJECTS_STATSプロシージャを使用して手動で収集する必要があります。固定オブジェクトには現行のデータベース・アクティビティが記録されます。データベースに典型的なアクティビティがあるときに統計を収集する必要があります。
ディクショナリ内で統計が変更されるたびに、後でリストアできるように前のバージョンの統計が自動的に保存されます。統計をリストアするには、DBMS_STATSパッケージのRESTOREプロシージャを使用します。 詳細は、「前のバージョンの統計のリストア」を参照してください。
「手動統計を使用する場合」で説明したように、揮発性の高い表など、表またはスキーマに関してDBMS_STATS_JOBプロセスによる新規統計の収集を中止する必要がある場合があります。このような場合は、DBMS_STATSパッケージに表またはスキーマの統計をロックするためのプロシージャが用意されています。 詳細は、「表統計またはスキーマ統計のロック」を参照してください。
自動統計収集を使用しないように選択した場合は、システム・スキーマを含め、すべてのスキーマ内で統計を手動で収集する必要があります。データベース内のデータが定期的に変化する場合は、統計がデータベース・オブジェクトの特性を正確に表すように、統計も定期的に収集する必要があります。
統計はDBMS_STATSパッケージを使用して収集されます。このPL/SQLパッケージは、統計の変更、表示、エクスポート、インポートおよび削除にも使用されます。
DBMS_STATSパッケージでは、表と索引の統計、および表の列とパーティションの個別の統計を収集できます。クラスタ統計は収集できません。ただし、DBMS_STATSを使用して、全クラスタのかわりに個別の表の統計を収集できます。
表、列または索引の統計を生成するとき、分析したオブジェクトの統計がすでにデータ・ディクショナリ内に収録されている場合、Oracleは既存の統計を更新します。古い統計は保存され、後で必要に応じてリストアできます。「前のバージョンの統計のリストア」を参照してください。
システム・スキーマの統計を収集する場合は、DBMS_STATS.GATHER_DICTIONARY_STATSプロシージャを使用できます。このプロシージャでは、SYSやSYSTEMを含むすべてのシステム・スキーマと、CTXSYSやDRSYSなどの他のオプション・スキーマの統計が収集されます。
データベース・オブジェクトの統計が更新されると、そのオブジェクトにアクセスする現在解析済のSQL文が無効にされます。文が次に実行されるときに、文が再解析され、オプティマイザは新しい統計に基づいて新しい実行計画を自動的に選択します。リモート・データベース上で新しい統計を持つオブジェクトにアクセスする分散型の文は、無効にされません。新しい統計は、次回にSQL文が解析されると有効になります。
表14-1は、DBMS_STATSパッケージにおけるデータベース・オブジェクトの統計収集のためのプロシージャです。
| プロシージャ | 収集対象 |
|---|---|
|
|
索引統計 |
|
|
表、列および索引の統計 |
|
|
スキーマ内のすべてのオブジェクトの統計 |
|
|
すべてのディクショナリ・オブジェクトの統計 |
|
|
データベース内のすべてのオブジェクトの統計 |
前述のプロシージャを統計収集に使用する場合は、次のようにいくつか重要な考慮事項があります。
統計収集操作では、サンプリングを使用して統計を予測できます。サンプリングは、統計収集の重要なテクニックです。サンプリングを使用せずに統計を収集するには、全表スキャンと表全体のソートが必要です。サンプリングを使用すると、統計収集に必要なリソースが最小限に抑えられます。
サンプリングは、DBMS_STATSプロシージャのESTIMATE_PERCENT引数を使用して指定します。サンプリング率は任意の値に設定できますが、必要な統計を正確に収集しながらパフォーマンスを最大限まで高めるために、DBMS_STATS収集プロシージャのESTIMATE_PERCENTパラメータをDBMS_STATS.AUTO_SAMPLE_SIZEに設定することをお薦めします。AUTO_SAMPLE_SIZEを使用すると、Oracleではオブジェクトの統計優先順位に基づいて適切な統計に必要な最適のサンプル・サイズが決定されます。統計のタイプごとに要件が異なるため、実際に取得されるサンプルのサイズは、表、列または索引間で異なる場合があります。たとえば、自動サンプリングでOEスキーマ内のすべての表に関する表統計および列統計情報を収集するには、次のように使用できます。
EXECUTE DBMS_STATS.GATHER_SCHEMA_STATS('OE',DBMS_STATS.AUTO_SAMPLE_SIZE);
ESTIMATE_PERCENTパラメータを手動で指定すると、指定されたパーセントで生成されたサンプルの大きさが十分でない場合に、DBMS_STATS収集プロシージャによりサンプリング・パーセントが自動的に増やされます。これによって、見積り値の変動が少なくなり、安定性が保証されます。
統計の収集操作は、シリアルまたはパラレルのどちらでも実行できます。並列度は、DBMS_STATS収集プロシージャのDEGREE引数で指定できます。パラレル統計収集はサンプリングと併用できます。DEGREEパラメータをDBMS_STATS.AUTO_DEGREEに設定することをお薦めします。このように設定すると、Oracleはオブジェクトのサイズとパラレル関連のinit.oraパラメータの設定に基づいて適切な並列度を選択できます。
クラスタ索引、ドメイン索引およびビットマップ結合索引など、特定のタイプの索引統計は、パラレルでは収集されないことに注意してください。
パーティション表および索引に対して、DBMS_STATSは、各パーティションの個別の統計を収集できます。また、全表または全索引のグローバル統計も収集できます。コンポジット・パーティションについても同様に、DBMS_STATSはサブパーティション、パーティション、全表および全索引の個別の統計を収集できます。収集するパーティション統計のタイプは、DBMS_STATS収集プロシージャのGRANULARITY引数で指定します。
最適化されたSQL文によっては、オプティマイザがパーティション(サブパーティション)統計またはグローバル統計の使用を選択する場合があります。どちらのタイプの統計もほとんどのアプリケーションにとって重要であり、GRANULARITYパラメータをAUTOに設定して両方のタイプのパーティション統計を収集することをお薦めします。
表の統計を収集する場合、DBMS_STATSでは表内の列のデータ配分情報が収集されます。データ配分に関して最も基本的な情報は、列の最大値と最小値です。ただし、列のデータに偏りがある場合、このレベルの統計ではオプティマイザのニーズが十分に満たされない場合があります。データ配分に偏りがある場合は、指定した列のデータ配分を記述するヒストグラムも列統計の一部として作成できます。 ヒストグラムの詳細は、「ヒストグラムの表示」を参照してください。
ヒストグラムは、DBMS_STATS収集プロシージャのMETHOD_OPT引数を使用して指定します。METHOD_OPTはFOR ALL COLUMNS SIZE AUTOに設定することをお薦めします。この設定では、どの列にヒストグラムが必要であるかということと各ヒストグラムのバケット数(サイズ)が、Oracleにより自動的に判別されます。また、これらの情報は手動でも指定できます。
データベースは時間の経過につれて変更されるため、その統計を定期的に収集する必要があります。特定のデータベース・オブジェクトに新規データベース統計が必要かどうかを判別するために、Oracleには表監視機能が用意されています。この監視機能は、STATISTICS_LEVELがTYPICALまたはALLに設定されている場合にデフォルトで有効になります。監視では、最新の統計収集以降の、表に対するINSERT、UPDATEおよびDELETEの概数と、その表が切り捨てられているかどうかを追跡します。表の変更情報は、USER_TAB_MODIFICATIONSビューで表示できます。データ変更後は、このビューに情報が伝播するまでに数分の遅延が発生することがあります。メモリーに保存されている未処理の監視情報を即時に反映させるには、DBMS_STATS.FLUSH_DATABASE_MONITORING_INFOプロシージャを使用します。
OPTIONSパラメータをGATHER STALEまたはGATHER AUTOに設定すると、GATHER_DATABASE_STATSまたはGATHER_SCHEMA_STATSプロシージャは、統計が失効している表に関して新規の統計を収集します。監視される表の変更が10%を超えた場合、これらの統計は失効したものとみなされ、再度収集されます。
ユーザー定義のオプティマイザ統計を作成して、ユーザー定義の索引およびファンクションをサポートできます。統計タイプを列またはドメイン索引に対応付ける場合、データベース・オブジェクトの統計が収集されるたびに、Oracleでは統計タイプの統計コレクション・メソッドがコールされます。
Oracleにより式が表すのと同等の列統計情報を収集できるように、ファンクション索引の作成後に表の新規列統計を収集する必要があります。そのためには、METHOD_OPT引数をFOR ALL HIDDEN COLUMNSに設定して統計収集プロシージャをコールします。
統計を手動で収集する場合は、その収集方法を決定するのみでなく、新規統計の収集時期と頻度も決定する必要があります。
表の増分変更が行われるアプリケーションの場合は、新規の統計を週または月に1回収集するのみで良い場合があります。このような環境で最も簡単な統計収集方法は、スクリプトまたはジョブ・スケジューリング・ツールを使用して、GATHER_SCHEMA_STATSおよびGATHER_DATABASE_STATSプロシージャを定期的に実行することです。収集の頻度によって、統計収集プロセスで起こるオーバーヘッドの処理に対し、オプティマイザの正確な統計を出すタスクのバランスをとります。
バルク・ロードを使用する場合など、バッチ操作で逐次変更される表の場合は、その表の統計をバッチ操作の一部として収集する必要があります。ロード操作の完了直後にDBMS_STATSプロシージャをコールしてください。
パーティション表の場合、通常は1つのパーティションのみが変更されます。このような場合は、表全体の統計を収集するのではなく、変更があったパーティションの統計のみを収集できます。ただし、パーティション表のグローバル統計の収集も必要な場合があります。
システム統計は、問合せオプティマイザに対してシステムのハードウェア特性(I/OとCPUのパフォーマンスおよび使用率など)を記述します。実行計画の選択時に、オプティマイザで各問合せに必要なI/OおよびCPUリソースが見積もられます。システム統計を使用すると、問合せオプティマイザはI/OおよびCPUコストをより正確に見積もることができ、問合せオプティマイザはより適切な実行計画を選択できます。
システム統計を収集するとき、指定された期間のシステム・アクティビティ(作業負荷統計)が分析されるか、作業負荷(非作業負荷統計)がシミュレートされます。統計は、DBMS_STATS.GATHER_SYSTEM_STATSプロシージャを使用して収集されます。システム統計を収集することをお薦めします。
表14-2に、DBMS_STATSパッケージにより収集されたオプティマイザのシステム統計と、特定のシステム統計の収集または手動設定のオプションを示します。
表、索引、列の統計とは異なり、システム統計の更新時には、すでに解析されているSQL文は無効にされません。新しいSQL文はすべて、新しい統計を使用して解析されます。
システム統計の収集方法には2つのオプションがあります。
これらのオプションは、物理データベースおよび作業負荷の収集プロセスを容易に使用できるようにします。作業負荷システム統計が収集されると、非作業負荷システム統計は無視されます。非作業負荷システム統計は、データベースの初回の起動時にデフォルト値に初期化されます。
Oracle 9i で導入された作業負荷統計は、シングルおよびマルチブロックの読取り時間、mbrc、CPU速度(cpuspeed)、最大システム・スループットおよび平均スレーブ・スループットを収集します。sreadtim、mreadtimおよびmbrcは、作業負荷の開始から終了までの2点間の、物理的な順次およびランダム読取りの数を比較して計算されます。これらの値は、バッファ・キャッシュが同期読取り要求を完了したときに変更されるカウンタを通して実装されます。このカウンタはバッファ・キャッシュ内にあるため、これらにはI/O遅延のみならず、ラッチの競合およびタスク・スイッチングに関連する待機も含まれています。このように、作業負荷統計は、作業負荷ウィンドウでシステムが実行するアクティビティに応じて異なります。ラッチ競合およびI/Oスループットの両方でシステムがI/Oバウンドの場合、この状態は統計に反映され、この統計が使用された後でI/O低減化集中計画が促進されます。さらに、作業負荷統計収集は、追加のオーバーヘッドを生成しません。
リリース9.2では、全表スキャン(FTS)の下限を設定するための最大I/Oスループットおよび平均スレーブ・スループットが追加されました。
作業負荷統計を収集するには、次のいずれかの手順を実行します。
dbms_stats.gather_system_stats('start')プロシージャを実行し、作業負荷ウィンドウの終了時にdbms_stats.gather_system_stats('stop')プロシージャを実行します。
dbms_stats.gather_system_stats('interval', interval=>N)を実行します。Nは、統計収集が自動停止する時間(分)です。
システム統計を削除するには、dbms_stats.delete_system_stats()を実行します。作業負荷統計が削除され、デフォルトの非作業負荷統計にリセットされます。
リリース10.2では、オプティマイザは全表スキャン(FTS)の実行時にmbrcの値を使用します。db_file_multiblock_read_countの値は、デフォルトでオペレーティング・システムが許可する最大値に設定されます。ただし、オプティマイザはコスト計算にmbrc=8を使用します。実際のmbrcは、その中間値になります。いくつかのブロックがバッファ・キャッシュに確保されている場合、またはセグメント・サイズが読込みサイズより小さい場合、シリアル・マルチブロック読込み要求がバッファ・キャッシュで処理され、2つ以上の要求に分割されるためです。作業負荷統計の一部として収集されたmbrc値は、このようにFTSの見積りに有用です。
作業負荷統計の収集プロセスでシリアル作業負荷の間に表スキャンが実行されない場合(OLTPシステムでしばしば発生します)、mbrcおよびmreadtimが収集されない場合があります。一方、DSSシステムではFTSが頻繁に実行されますが、パラレル実行によってバッファ・キャッシュがバイパスされる可能性があります。このような場合、バッファ・キャッシュを使用して索引参照が実行されるため、sreadtimが収集されます。mbrcまたはmreadtimを収集できないか、または収集してもそれらの検証ができない場合で、sreadtimおよびcpuspeedが収集済の場合は、sreadtimおよびcpuspeedのみがコスト計算に使用されます。FTSコストは、前のリリースで実装された分析アルゴリズムを使用して計算されます。mbrcおよびmreadtimを計算するもう1つの方法は、FTSを強制的にシリアル・モードにしてオプティマイザでデータを収集できるようにする方法です。
非作業負荷統計は、I/O転送速度、I/Oシーク時間およびCPU速度(cpuspeednw)で構成されています。作業負荷統計と非作業負荷統計の主な違いは、収集方法にあります。
非作業負荷統計は、すべてのデータ・ファイルに対してランダム読取りを発行してデータを収集しますが、作業負荷統計は、データベース・アクティビティの発生時に更新されるカウンタを使用します。isseektimは、ディスク・ヘッドがデータを読み取る位置に移動する時間を表します。この値は、ディスクの回転速度およびディスクまたはRAIDの仕様に応じて5ミリ秒〜15ミリ秒の間で変化します。I/O転送速度は、オペレーティング・システムの1つのプロセスでI/Oサブシステムからのデータの読取りが可能な速度を表します。この値は、毎秒数MBから数百MBまで大きく変化します。Oracleでは、I/O転送速度に比較的低い値のデフォルト設定を使用しています。
Oracle 10g では、非作業負荷統計およびCPUコスト・モデルをデフォルトで使用しています。非作業負荷統計の値は、最初のインスタンス起動時にデフォルトに初期化されます。
ioseektim = 10ms iotrfspeed = 4096 bytes/ms cpuspeednw = gathered value, varies based on system
作業負荷統計が収集されると非作業負荷統計は無視され、かわりに作業負荷統計が使用されます。
非作業負荷統計を収集するには、引数なしでdbms_stats.gather_system_stats()を実行します。非作業負荷統計の収集プロセスの間、I/Oシステムにオーバーヘッドが発生します。この収集プロセスは、I/Oのパフォーマンスおよびデータベースのサイズによって数秒から数分かかることがあります。
この情報は分析され、整合性が検証されます。場合により、非作業負荷統計の値はデフォルト値のままになることがあります。このような場合は、統計収集プロセスを繰り返すか、dbms_stats.set_system_statsプロシージャを使用してI/Oシステムの仕様に応じた値を手動で設定します。
この項では、次の内容を説明します。
ディクショナリ内で統計が変更されるたびに、後でリストアできるように前のバージョンの統計が自動的に保存されます。統計をリストアするには、DBMS_STATSパッケージのRESTOREプロシージャを使用します。これらのプロシージャは、引数としてタイムスタンプを使用し、そのタイムスタンプでの統計をリストアします。これは、新規に収集された統計では不適切な実行計画が作成され、管理者が前の統計セットに戻す必要がある場合に役立ちます。
統計の変更時刻を表示するディクショナリ・ビューがあります。これらのビューは、統計のリストアに使用するタイムスタンプを判断する場合に役立ちます。
DBA_OPTSTAT_OPERATIONSには、DBMS_STATSを使用してスキーマ・レベルとデータベース・レベルで実行された統計操作の履歴が含まれます。
*_TAB_STATS_HISTORYビュー(ALL、DBAまたはUSER)には、表統計の変更履歴が含まれます。
古い統計は、統計履歴の保存設定とシステムの最終分析時刻に基づいて、定期的かつ自動的に消去されます。保存期間は、DBMS_STATSのALTER_STATS_HISTORY_RETENTIONプロシージャを使用して構成可能です。デフォルト値は31日で、オプティマイザ統計を過去31日の任意の時点までリストアできることを意味します。
自動消去は、STATISTICS_LEVELパラメータがTYPICALまたはALLに設定されている場合に有効になります。自動消去が無効になっている場合は、PURGE_STATSプロシージャを使用して古いバージョンの統計を手動で消去する必要があります。
統計のリストアおよび消去に関連する他のDBMS_STATSプロシージャは、次のとおりです。
PURGE_STATS: このプロシージャを使用すると、タイムスタンプを超える古いバージョンを手動で消去できます。
GET_STATS_HISTORY_RENTENTION: このファンクションを使用すると、現行の統計履歴の保存値を取得できます。
GET_STATS_HISTORY_AVAILABILTY: このファンクションを使用すると、統計履歴が使用可能な最も古いタイムスタンプを取得できます。最も古いタイムスタンプより前のタイムスタンプには、統計をリストアできません。
前のバージョンの統計をリストアする場合は、次の制限が適用されます。
統計をデータ・ディクショナリからエクスポートして、ユーザー所有の表にインポートできます。これにより、同じスキーマについて複数バージョンの統計を作成できます。また、データベース間で統計のコピーもできます。この操作により、統計を本番データベースから小規模なテスト・データベースにコピーできます。
統計をエクスポートする前に、その統計を保持する表を作成する必要があります。この統計表を作成するには、DBMS_STATS.CREATE_STAT_TABLEプロシージャを使用します。この表の作成後に、DBMS_STATS.EXPORT_*_STATSプロシージャを使用して、データ・ディクショナリから統計表に統計をエクスポートできます。その後、DBMS_STATS.IMPORT_*_STATSプロシージャを使用して統計をインポートします。
オプティマイザでは、ユーザー所有の表に格納されている統計が使用されないことに注意してください。オプティマイザで使用されるのは、データ・ディクショナリに格納されている統計のみです。ユーザー所有の表内の統計をオプティマイザで使用するには、統計インポート・プロシージャを使用して、その統計をデータ・ディクショナリにインポートする必要があります。
統計をデータベース間で移動するには、最初のデータベース上の統計をエクスポートしてから、EXPおよびIMPユーティリティまたは他のメカニズムを使用して統計表を第2のデータベースにコピーし、最後に統計を第2のデータベースにインポートする必要があります。
統計リストア機能は、ある面では統計のインポートおよびエクスポート機能に類似しています。通常、次の場合にはリストア機能を使用する必要があります。
次の場合には、EXPORT/IMPORT_*_STATSプロシージャを使用する必要があります。
表またはスキーマの統計をロックできます。統計がロックされると、その統計はロックが解除されるまで変更できなくなります。これらのロック・プロシージャは、統計が変化しないことを保証する必要のある静的環境に役立ちます。
DBMS_STATSパッケージには、統計をロックするための2つのプロシージャと、統計のロックを解除するための2つのプロシージャが用意されています。
SET_*_STATISTICSプロシージャを使用して、表、列、索引およびシステムの統計を設定できます。統計が不正確であったり一貫性がないとパフォーマンスが低下するため、この方法での統計の設定はお薦めしません。
動的サンプリングの目的は、述語の選択性および表と索引に関する統計のより正確な見積りを判断して、サーバーのパフォーマンスを改善することです。表と索引に関する統計には、表ブロック・カウント、適用可能な索引ブロック・カウント、表のカーディナリティおよび関連する結合列の統計が含まれます。正確に見積ると、より適切な実行計画がオプティマイザで作成できます。
動的サンプリングを使用すると、次の作業が可能になります。
この動的サンプリング機能は、OPTIMIZER_DYNAMIC_SAMPLINGパラメータにより制御されます。動的サンプリングにより必要な統計を自動的に収集するには、このパラメータを2以上の値に設定する必要があります。 デフォルト値は2です。設定できるサンプリング・レベルの詳細は、「動的サンプリング・レベル」を参照してください。
重要なパフォーマンス属性は、コンパイル時に決定されます。Oracleでは、問合せで動的サンプリングを使用する利点があるかどうか、コンパイル時に判別されます。利点がある場合、再帰的SQL文が発行されて表のブロックの小さなランダム・サンプルがスキャンされ、関連する単一表の述語を適用することで述語の選択性の見積りが行われます。サンプルしたカーディナリティが、表のカーディナリティの見積りに使用される場合もあります。関連する列統計情報と索引統計情報も収集されます。
OPTIMIZER_DYNAMIC_SAMPLING初期化パラメータの値によって、動的サンプリングの問合せで読み取られるブロック数が決定します。
通常、迅速に(数秒以内で)完了する問合せに対しては、動的サンプリングのコストが発生するのは望ましくありません。しかし、次のいずれかの条件が当てはまる場合は、動的サンプリングが有効です。
動的サンプリングは、単一表の述語によるサブセットに適用したり、動的サンプリングが行われていない述語の通常の選択性の見積りと組み合せることができます。
動的サンプリングは、OPTIMIZER_DYNAMIC_SAMPLINGパラメータを使用して制御します。このパラメータの値は、0〜10に設定できます。デフォルトは2です。
0の場合、動的サンプリングが行われません。
動的サンプリングは、サンプリング対象の表内で行が挿入、削除または更新されていない場合、同じものが繰り返し使用されます。OPTIMIZER_FEATURES_ENABLEパラメータが9.2.0より前のリリースに設定されている場合、動的サンプリングはオフになります。
サンプリング・レベルは、使用された動的サンプリング・レベルがカーソル・ヒントまたはOPTIMIZER_DYNAMIC_SAMPLING初期化パラメータからの場合、次のようになります。
表の動的サンプリング・レベルがDYNAMIC_SAMPLINGオプティマイザ・ヒントを使用して設定されている場合のサンプリング・レベルは、次のとおりです。
Oracleでは、統計が欠落している表が検出されると、オプティマイザに必要な統計が動的に収集されます。ただし、ある種の表の場合、動的サンプリングは実行されません。これには、リモート表と外部表が含まれます。これらの場合および動的サンプリングが無効になっている場合、オプティマイザは統計にデフォルト値を使用します。表14-3および表14-4を参照してください。
| 表統計 | オプティマイザによって使用されるデフォルト値 |
|---|---|
|
|
ブロック数×(ブロック・サイズ-キャッシュ層)÷行の平均の長さ |
|
|
100バイト |
|
|
100、またはエクステント・マップに基づく実際の値 |
|
|
2000行 |
|
|
100バイト |
| 索引統計 | オプティマイザによって使用されるデフォルト値 |
|---|---|
|
|
1 |
|
|
25 |
|
|
1 |
|
|
1 |
|
|
100 |
|
|
800 |
この項では、次の内容を説明します。
表、索引および列の統計は、データ・ディクショナリに格納されます。データ・ディクショナリ内の統計を表示するには、適切なデータ・ディクショナリ・ビューを問い合せます(USER、ALLまたはDBA)。次のDBA_*ビューがあります。
列統計情報はヒストグラムとして格納できます。これらのヒストグラムは、列データの配分の正確な見積りを提供します。ヒストグラムによって、データが偏っている場合の選択性の見積りの精度が改善され、均一でないデータ配分が存在する最適な実行計画が得られます。
Oracleでは、列統計情報に高さ調整済ヒストグラムと頻度ヒストグラムという2つのタイプが使用されます。ヒストグラムのタイプは、*TAB_COL_STATISTICSビュー(USERおよびDBA)のHISTOGRAM列に格納されます。この列の値は、HEIGHT BALANCED、FREQUENCYまたはNONEです。
高さ調整済ヒストグラムでは、列値が帯域に分割され、各帯域にほぼ同数の行が存在するようになっています。したがって、ヒストグラムによって提示される有用な情報が存在するのは、値範囲の終点が位置するところです。
値が1〜100の間に存在し、ヒストグラムが10バケットである列Cについて検討します。Cのデータ配分が均一な場合のヒストグラムは、図14-1のようになります。数字は終点の値です。
各バケット内の行数は、表内の全行数の10分の1です。均一に分布しているこの例では、4/10の行の値が、60〜100の間にあります。
データ配分が均一でない場合のヒストグラムの例を図14-2に示します。
この場合、ほとんどの行で、この列の値が5になっています。60〜100の間の値を持っている行は、行全体の1/10のみです。
高さ調整済ヒストグラムは、例14-1に示すように*TAB_HISTOGRAMS表を使用して表示できます。
BEGIN DBMS_STATS.GATHER_table_STATS (OWNNAME => 'OE', TABNAME => 'INVENTORIES', METHOD_OPT => 'FOR COLUMNS SIZE 10 quantity_on_hand'); END; / SELECT column_name, num_distinct, num_buckets, histogram FROM USER_TAB_COL_STATISTICS WHERE table_name = 'INVENTORIES' AND column_name = 'QUANTITY_ON_HAND'; COLUMN_NAME NUM_DISTINCT NUM_BUCKETS HISTOGRAM ------------------------------ ------------ ----------- --------------- QUANTITY_ON_HAND 237 10 HEIGHT BALANCED SELECT endpoint_number, endpoint_value FROM USER_HISTOGRAMS WHERE table_name = 'INVENTORIES' and column_name = 'QUANTITY_ON_HAND' ORDER BY endpoint_number; ENDPOINT_NUMBER ENDPOINT_VALUE --------------- -------------- 0 0 1 27 2 42 3 57 4 74 5 98 6 123 7 149 8 175 9 202 10 353
問合せ出力では、ヒストグラム内で1行が1つのバケットに対応します。
頻度ヒストグラムでは、列の値がそれぞれヒストグラムの1つのバケットに対応します。各バケットには、その単一値の発生数が含まれます。個別値の個数が、指定されたヒストグラム・バケットの個数以下であれば、高さ調整済ヒストグラムのかわりに頻度ヒストグラムが自動的に作成されます。頻度ヒストグラムは、例14-2に示すように*TAB_HISTOGRAMS表を使用して表示できます。
BEGIN DBMS_STATS.GATHER_table_STATS (OWNNAME => 'OE', TABNAME => 'INVENTORIES', METHOD_OPT => 'FOR COLUMNS SIZE 20 warehouse_id'); END; / SELECT column_name, num_distinct, num_buckets, histogram FROM USER_TAB_COL_STATISTICS WHERE table_name = 'INVENTORIES' AND column_name = 'WAREHOUSE_ID'; COLUMN_NAME NUM_DISTINCT NUM_BUCKETS HISTOGRAM ------------------------------ ------------ ----------- --------------- WAREHOUSE_ID 9 9 FREQUENCY SELECT endpoint_number, endpoint_value FROM USER_HISTOGRAMS WHERE table_name = 'INVENTORIES' and column_name = 'WAREHOUSE_ID' ORDER BY endpoint_number; ENDPOINT_NUMBER ENDPOINT_VALUE --------------- -------------- 36 1 213 2 261 3 370 4 484 5 692 6 798 7 984 8 1112 9
|
![]() Copyright © 2000, 2008, Oracle Corporation. All Rights Reserved. |
|