by Hayato Matsuura.

アクセス述語とフィルタ述語の見分け方


Oracleはwhere句(述語)を適用するのに、 3つの方法を使い分けます。

アクセス述語 (「access」)

アクセス述語は、リーフノードの走査の開始と終了の条件を表しています。

インデックスフィルタ述語 (インデックス操作に対する「filter」)

インデックスフィルタ述語は、リーフノード走査の時にのみ適用されます。スキャンされる範囲の開始と終了の条件を表したり、 範囲を狭めるものとしては使われません。

テーブルレベルのフィルタ述語 (テーブル操作に対する「filter」)

インデックスの一部でない列に対する述語は、テーブルのレベルで評価されます。その場合データベースは、 まずテーブルから行をロードしなければなりません。

注記

インデックスフィルタ述語は、間違った安心感を持ってしまう原因になりかねません。 インデックスは確かに使われますが、データ量やシステムの負荷が増大すると、 急激にパフォーマンス劣化が起きる可能性があります。

DBMS_XPLANユーティリティ(実行計画の表示方法を参照)を使って生成された実行計画は、 以下のような実行計画の表の「Predicate Information」セクションで、インデックスの使用状況について表示します。

------------------------------------------------------
| Id | Operation         | Name       | Rows  | Cost |
------------------------------------------------------
|  0 | SELECT STATEMENT  |            |     1 | 1445 |
|  1 |  SORT AGGREGATE   |            |     1 |      |
|* 2 |   INDEX RANGE SCAN| SCALE_SLOW |  4485 | 1445 |
------------------------------------------------------

Predicate Information (identified by operation id):
   2 - access("SECTION"=:A AND "ID2"=:B)
       filter("ID2"=:B)

述語情報の番号は、実行計画の「Id」列に対応しています。 見ての通り、述語情報のある処理にはアスタリスクマークが付いています。

協力してください

この記事が気に入ったら、私の書いた本「SQLパフォーマンス詳解」や私によるトレーニングもきっと気にいるはず。

パフォーマンスとスケーラビリティの 章から抜粋したこの例では、INDEX RANGE SCANがアクセス述語と フィルタ述語を持っていると表示されています。Oracleは、フィルタ述語をアクセス述語としても表示する特徴があります。この実行計画にある ID2=:Bがその例です。

重要

条件がフィルタ述語として表示されていれば、それはフィルタ述語です。アクセス述語と表示されていても関係ありません。

従ってこの例でINDEX RANGE SCANは、 "SECTION"=:Aの条件の範囲全体をスキャンし、 各行に対して"ID2"=:Bのフィルタを適用します。

テーブルレベルでのフィルタ述語は、TABLE ACCESS BY INDEX ROWIDTABLE ACCESS FULLと言った対応するテーブルアクセスに対して表示されます。

ツールが違えば述語情報も違って表示される事に注意しましょう。例えば、Oracle SQL Developerでは述語情報を以下のように対応する処理の下に表示します。

図A.1Oracle SQL Developerにおけるアクセス述語とフィルタ述語

ツールによっては述語情報を表示してくれないものもあります。「実行計画の表示方法」で説明した DBMS_XPLANに立ち返るようにしましょう。

著者について

Markus Winandの写真

Markus Winand氏は、開発者がSQLパフォーマンスを改善するお手伝いをしています。彼は、SQL Performance Explainedの 著者でもあり、出張トレーニングhttp://winand.at/での リモート講義も 行っています。

彼の本

カバー『SQLパフォーマンス詳解』

核心をわかりやすく 解説。

Markusから購入します
(送料無料+PDF)

Amazonで購入
(印刷版のみ)

Do not use offset for pagination

Learn why

Visit my sibling!A lot changed since SQL-92!

Use The Index, Luke のカップは

ステッカー、コースター、本、コーヒーマグ。 学習に必要なものすべて。

今すぐ購入

Connect with Markus Winand

Markus Winand on LinkedInMarkus Winand on XINGMarkus Winand on Twitter
“Use The Index, Luke!” by Markus Winand is licensed under a Creative Commons Attribution-Noncommercial-No Derivative Works 3.0 Unported License.
法律上の通知 | お問い合わせ | 無保証 | 商標 | プライバシーとGDPR | CC-BY-NC-ND 3.0 license