6.9.2.2 PGQL問合せでのパフォーマンスの考慮事項
次に、問合せのパフォーマンスのためのお薦めの慣例をいくつか示します。
再帰的問合せ
再帰的問合せの実行を高速化するために、次の索引をお薦めします。
- 再帰パターンの基礎となるVERTEX表の場合、キー列の索引
- 再帰パターンの基礎となるEDGE表の場合、ソース・キー列の索引
ノート:
(ソース・キー, 宛先キー)に索引を作成することもできます。
たとえば、次のCREATE PROPERTY GRAPH文について考えてみます。
CREATE PROPERTY GRAPH people
VERTEX TABLES(
person
KEY ( id )
LABEL person
PROPERTIES( name, age )
)
EDGE TABLES(
knows
key (person1, person2)
SOURCE KEY ( person1 ) REFERENCES person (id)
DESTINATION KEY ( person2 ) REFERENCES person (id)
NO PROPERTIES
)
OPTIONS ( PG_VIEW )
また、次の問合せも考えてみます。
SELECT COUNT(*)
FROM MATCH ANY SHORTEST ( (n:Person) -[e:knows]->* (m:Person) )
WHERE n.id = 1234
前述の問合せの再帰的部分のパフォーマンスを向上させるには、次の索引が存在する必要があります。
CREATE INDEX <INDEX_NAME> ON PERSON(ID)
CREATE INDEX <INDEX_NAME> ON KNOWS(PERSON1)
またはCREATE INDEX <INDEX_NAME> ON KNOWS(PERSON1, PERSON2)
コンポジット頂点キー
コンポジット頂点キーの場合、キー列にファンクション索引を作成することで、問合せの実行を最適化できます。
- 再帰パターンの基礎となるVERTEX表の場合、カンマ区切りのキー列の連結に対するファンクション索引
- 再帰パターンの基礎となるEDGE表の場合、カンマ区切りのソース・キー列の連結に対するファンクション索引
ノート:
(ソース・キー列, 宛先キー列)に索引を作成することもできます。
たとえば、次のCREATE PROPERTY GRAPH文について考えてみます。
CREATE PROPERTY GRAPH people
VERTEX TABLES(
person
KEY ( id1, id2 )
LABEL person
PROPERTIES( name, age )
)
EDGE TABLES(
knows
key (id)
SOURCE KEY ( id1person1, id2person1 ) REFERENCES person (id1,id2)
DESTINATION KEY ( id1person2, id2person2 ) REFERENCES person (id1,id2)
NO PROPERTIES
)
OPTIONS ( PG_VIEW )
また、次の問合せも考えてみます。
SELECT COUNT(*)
FROM MATCH ANY SHORTEST ( (n:Person) -[e:knows]->* (m:Person) )
WHERE n.id = 1234
前述の問合せの再帰的部分のパフォーマンスを向上させるには、次の索引が存在する必要があります。
CREATE INDEX <INDEX_NAME> ON PERSON (ID1 || ',' || ID2)
CREATE INDEX <INDEX_NAME> ON KNOWS (ID1PERSON1 || ',' || ID2PERSON1)
またはCREATE INDEX <INDEX_NAME> ON KNOWS (ID1PERSON1 || ',' || ID2PERSON1, ID1PERSON2 || ',' || ID2PERSON2)
コンポジット頂点キーの一部の列が文字列列である場合、その列は、ファンクション索引の作成でカンマをエスケープする必要があります。
たとえば、前述の例の表PERSON
の列ID1
の型がVARCHAR2(10)
の場合、次のように列のカンマをエスケープする必要があります。
replace(ID1, ',', '\,')
そのため、パフォーマンスを向上させるための索引は次のようになります。
CREATE INDEX <INDEX_NAME> ON PERSON (replace(ID1, ',', '\,') || ',' || ID2)
CREATE INDEX <INDEX_NAME> ON KNOWS (replace(ID1PERSON1, ',', '\,') || ',' || ID2PERSON1)
問合せオプティマイザ・ヒントの使用
次のヒントを使用すると、PGQL可変長パス・パターンのSQLへの変換に影響を与えることができます。
REVERSE_PATH
: 逆パス最適化のオンとオフを切り替えます(デフォルトではON
)。ON
の場合、指定されたフィルタ述語に基づいて、パターンを最適に評価できるは、ソースから宛先なのか宛先からソースなのかを自動的に判断します。PUSH_SRC_HOPS
: ソース・フィルタ最適化の強要のオンとオフを切り替えます(デフォルトではON
)。ON
の場合、フィルタ述語を使用して、ソース頂点(パス評価が逆の場合は宛先頂点)の数を制限し、それによって可変長パス・パターン評価の検索領域を制限します。PUSH_DST_HOPS
: 宛先フィルタ最適化の強要のオンとオフを切り替えます(デフォルトではOFF
)。ON
の場合、フィルタ述語を使用して、宛先頂点(パス評価が逆の場合はソース頂点)の数を制限し、それによって可変長パス・パターン評価の検索領域を制限します。
前述のヒントは、次のJava APIメソッドでoptions
パラメータとして構成できます。
executeQuery(String pgql, String options)
translateQuery(String pgql, String options)
execute(String pgql, String matchOptions, String options)
たとえば、次のPGQL問合せについて考えます。
SELECT v1.name AS v1, v2.name AS v2, v3.name As v3
FROM MATCH (v1:Person)-[e1:friendOf]->(v2:Person),
MATCH ANY (v2:Person)-[e2:friendOf]->*(v3:Person)
WHERE v1.name= 'Bob'
PUSH_SRC_HOPS
のデフォルト・オプションを使用して前述の問合せを実行すると、次のようにstart_nodes_translation
の出力にフィルタ式が表示されます。
System.out.println(pgqlStatement.translateQuery(pgql).getSqlTranslation())
...
...
start_nodes_translation => (to_clob('SELECT ''PERSONS'' AS "src_table", e1.person_b AS "src_key"
FROM "GRAPHUSER"."PERSONS" "V1", "GRAPHUSER"."FRIENDSHIPS" "E1"
WHERE (((e1.person_a = v1.person_id) AND NOT(e1.person_b IS NULL)) AND (v1.name = ''Bob''))')),
end_nodes_translation => (to_clob('SELECT ''PERSONS'' AS "dst_table", v3.person_id AS "dst_key"
FROM "GRAPHUSER"."PERSONS" "V3"')),
...
...
ヒントPUSH_SRC_HOPS=F
を指定して前述の問合せを実行すると、次のように問合せはSQLに変換されます。
System.out.println(pgqlStatement.translateQuery(pgql,"PUSH_SRC_HOPS=F").getSqlTranslation())
...
...start_nodes_translation => (to_clob('SELECT ''PERSONS'' AS "src_table", v2.person_id AS "src_key"
FROM "GRAPHUSER"."PERSONS" "V2"')),
end_nodes_translation => (to_clob('SELECT ''PERSONS'' AS "dst_table", v3.person_id AS "dst_key"
FROM "GRAPHUSER"."PERSONS" "V3"')),
...
...
グラフ・メタデータ・キャッシュおよび変換キャッシュを使用した問合せ変換の高速化
次のグローバル・キャッシュは、PGQL問合せ変換の高速化に役立ちます。
- グラフ・メタデータ・キャッシュ: 表、ラベル、プロパティなどのグラフ・メタデータを格納します。
- 変換キャッシュ: PGQLからSQLへの変換を格納します。
次のJava APIを使用してキャッシュを構成できます。
clearTranslationCache()
disableTranslationCache()
enableTranslationCache()
setTranslationCacheMaxCapacity(int maxCapacity)
clearGraphMetadataCache()
disableGraphMetadataCache()
enableGraphMetadataCache()
setGraphMetadataCacheMaxCapacity(int maxCapacity)
前述のこれらのメソッドは、PgqlConnection
クラスに属します。個々のキャッシュはデータベース・ユーザーごとに保持されるため、キャッシュされたオブジェクトは、接続URLとその下のユーザーが同じである場合に、異なるPgqlConnection
オブジェクト間で共有されます。
親トピック: プロパティ・グラフ・ビューに対するPGQL問合せの実行