すべての eXtreme Scale 照会には照会計画があります。この計画は、照会エンジンが ObjectMap および索引とどのように対話するかを説明するものです。照会計画を表示すると、照会ストリングまたは索引が適切に使用されているかどうかを判断できます。また照会計画を使用すると、照会ストリング中のわずかな変更が eXtreme Scale による照会の実行方法に及ぼす変化を検討することもできます。
照会計画は、以下のいずれかの手段で表示できます。
照会計画は、ObjectGrid トレースを使用して表示できます。照会計画トレースを有効とするには、以下のトレース仕様を使用します。
QueryEnginePlan=debug=enabled
トレース・ログ・ファイルを有効にする方法およびその検出方法について詳しくは、トレースの収集を参照してください。
この照会計画では、for という単語を使用して、この照会が ObjectMap コレクションで繰り返されるか、または派生するコレクション (q2.getEmps()、q2.dept、または内部ループによって返される一時的コレクションなど) で繰り返されることを示します。コレクションが ObjectMap のコレクションである場合、照会計画は、順次スキャン (INDEX SCAN で指示) や固有または非固有の索引が使用されているかどうかを示します。また、照会計画ではフィルター・ストリングを使用して、コレクションに適用される条件式をリストします。
通常、デカルト積は対象照会では使用されません。以下の照会では、外部ループ内の EmpBean マップ全体をスキャンし、内部ループ内の DeptBean マップ全体をスキャンします。
SELECT e, d FROM EmpBean e, DeptBean d
Plan trace:
for q2 in EmpBean ObjectMap using INDEX SCAN
for q3 in DeptBean ObjectMap using INDEX SCAN
returning new Tuple( q2, q3 )
以下の照会では、EmpBean マップを順次スキャンして特定部門の全従業員名を検索し、従業員オブジェクトを取得します。この照会では、従業員オブジェクトからその部門オブジェクトにナビゲートして、d.no=1 フィルターを適用します。この例の場合、各従業員はただ 1 つの部門オブジェクト参照を持つため、内部ループが 1 回実行されます。
SELECT e.name FROM EmpBean e JOIN e.dept d WHERE d.no=1
Plan trace:
for q2 in EmpBean ObjectMap using INDEX SCAN
for q3 in q2.dept
filter ( q3.getNo() = 1 )
returning new Tuple( q2.name )
以下の照会は、前記の照会と同等です。ただし、以下の照会では、まず DeptBean 1 次キー・フィールド番号に対して定義された固有索引を使用することで、結果が 1 つの部門オブジェクトに絞り込まれるため、実行効率が高まります。照会により、この部門オブジェクトから従業員オブジェクトにナビゲートされ、以下のように従業員名が取得されます。
SELECT e.name FROM DeptBean d JOIN d.emps e WHERE d.no=1
Plan trace:
for q2 in DeptBean ObjectMap using UNIQUE INDEX key=(1)
for q3 in q2.getEmps()
returning new Tuple( q3.name )
以下の照会を使用して、開発または販売に従事するすべての従業員を検索します。この照会では、EmpBean マップ全体をスキャンするとともに、式 d.name = 'Sales' or d.name='Dev' を評価することで追加のフィルタリングを実行します。
SELECT e FROM EmpBean e, in (e.dept) d WHERE d.name = 'Sales'
or d.name='Dev'
Plan trace:
for q2 in EmpBean ObjectMap using INDEX SCAN
for q3 in q2.dept
filter (( q3.getName() = Sales ) OR ( q3.getName() = Dev ) )
returning new Tuple( q2 )
以下の照会は前記の照会と同等ですが、この照会では異なる照会計画を実行し、フィールド名について作成された範囲索引を使用します。一般的に、部門オブジェクトの範囲の絞り込みに名前フィールドの索引が使用されることにより、開発または販売部門がごく少数である場合は照会が高速実行されるため、この照会の方が性能が高くなります。
SELECT e FROM DeptBean d, in(d.emps) e WHERE d.name='Dev' or d.name='Sales'
Plan trace:
IteratorUnionIndex of
for q2 in DeptBean ObjectMap using INDEX on name = (Dev)
for q3 in q2.getEmps()
for q2 in DeptBean ObjectMap using INDEX on name = (Sales)
for q3 in q2.getEmps()
以下の照会を使用して、従業員のいない部門を検索します。
SELECT d FROM DeptBean d WHERE NOT EXISTS(select e from d.emps e)
Plan trace:
for q2 in DeptBean ObjectMap using INDEX SCAN
filter ( NOT EXISTS ( correlated collection defined as
for q3 in q2.getEmps()
returning new Tuple( q3 )
returning new Tuple( q2 )
以下の照会は前述の照会と同等ですが、この照会では SIZE スカラー関数が使用されます。この照会でパフォーマンスは同じですが、作成が容易になっています。
SELECT d FROM DeptBean d WHERE SIZE(d.emps)=0
for q2 in DeptBean ObjectMap using INDEX SCAN
filter (SIZE( q2.getEmps()) = 0 )
returning new Tuple( q2 )
以下の例は、同様の性能を持つ前述の照会と同じ照会を書き込む別の方法を示していますが、この照会も容易に書き込むことができます。
SELECT d FROM DeptBean d WHERE d.emps is EMPTY
Plan trace:
for q2 in DeptBean ObjectMap using INDEX SCAN
filter ( q2.getEmps() IS EMPTY )
returning new Tuple( q2 )
以下の照会では、パラメーターの値と等しい名前を持つ従業員の住所のうち少なくとも 1 つと一致する住所を持つすべての従業員を検索します。内部ループは外部ループに依存関係を持ちません。この照会では、内部ループは 1 回実行されます。
SELECT e FROM EmpBean e WHERE e.home = any (SELECT e1.home FROM EmpBean e1
WHERE e1.name=?1)
for q2 in EmpBean ObjectMap using INDEX SCAN
filter ( q2.home =ANY temp collection defined as
for q3 in EmpBean ObjectMap using INDEX on name = ( ?1)
returning new Tuple( q3.home )
)
returning new Tuple( q2 )
以下の照会は前述の照会と同等ですが、この照会には相関副照会があり、さらに内部ループが繰り返し実行されます。
SELECT e FROM EmpBean e WHERE EXISTS(SELECT e1 FROM EmpBean e1 WHERE
e.home=e1.home and e1.name=?1)
Plan trace:
for q2 in EmpBean ObjectMap using INDEX SCAN
filter ( EXISTS ( correlated collection defined as
for q3 in EmpBean ObjectMap using INDEX on name = (?1)
filter ( q2.home = q3.home )
returning new Tuple( q3 )
returning new Tuple( q2 )