インデックスを使用する

グラフ・クエリー用インデックスの使用。

V()ステップの後の最初の探索ステップに対して、グラフ探索クエリーでグローバル・インデックスが使用できます。最初にフェッチされる頂点の数を削減するために使用されます。グローバル・インデックス作成に複数のプロパティを使用する場合は、検索インデックスを使用する必要があることに注意してください。一般的に、探索ステップには頂点ラベルが関与し、プロパティ・キーと特定のプロパティ値を含めることができます。探索では、g.V()に続くステップは、通常はインデックスを探索するステップになります。中間探索V()ステップが呼び出された場合は、インデックスを使用した追加のステップを利用して、探索される頂点のリストを絞り込むことができます。

注: グラフ探索では、頂点ラベルとプロパティ・キーの両方が指定されている場合にのみインデックスを使用します。両方が指定されていない場合、インデックスは使用されず、プロパティ・キーのフル・グラフ・スキャンが行われます。フル・グラフ・スキャンが無効になっている場合、この例に示すように、クエリーは失敗に終わります。この例では、プロパティが指定されていますが、頂点ラベルは指定されていません。
g.V().has('name','Julia Child')
Could not find an index to answer query clause and graph.allow_scan is disabled: 
((label = FridgeSensor & name WITHIN [Julia Child]) | (label = author & name WITHIN [Julia Child]) | 
(label = book & name WITHIN [Julia Child]) | (label = ingredient & name WITHIN [Julia Child]) | 
(label = meal & name WITHIN [Julia Child]) | (label = recipe & name WITHIN [Julia Child]) | 
(label = reviewer & name WITHIN [Julia Child]))

グローバル・インデックスが開始頂点を見つけた後、エッジ・インデックスとプロパティ・インデックス(頂点中心インデックス)を使用してクエリーを絞り込むことができます。これらのインデックスでは、クエリーをさらに制限するために使用されるエッジまたはメタプロパティの定義が許可されています。

手順

グローバル・インデックス
  • ここに示すグラフ探索では、インデックスを使用して特定のperson頂点を検出してクエリーを開始します。
    g.V().has(person, 'name', 'Emeril Lagasse').out('created').values('name')

    このグラフ探索では、インデックスが存在する場合は、インデックスを使用します。探索ステップhas('person', 'name', 'Emeril Lagasse')では、インデックスが作成されている頂点ラベルとプロパティ・キーを識別します。探索の起点となる最初のインデックスが検出されると、出力エッジcreatedがウォークスルーされ、隣接する頂点がname別にリストされます。このグラフ探索は、頂点ラベルとプロパティ・キーを併用することの重要性を示しています。人物とレシピという2つの異なる要素が同じプロパティ・キーnameを使用しているためです。

    インデックスの使用については、profile()メソッドを使用して確認します。
    gremlin> g.V().has('person', 'name', 'Emeril Lagasse').out('created').values('name').profile()
    ==>Traversal Metrics
    Step                                                               Count  Traversers       Time (ms)    % Dur
    =============================================================================================================
    DsegGraphStep(vertex,[],(label = person & name ...                     1           1           8.427    27.42
      query-optimizer                                                                              0.792
        \_condition=((label = person & name = Emeril Lagasse) & (true))
      query-setup                                                                                  0.028
        \_isFitted=true
        \_isSorted=false
        \_isScan=false
      index-query                                                                                  6.514
        \_indexType=Materialized
        \_usesCache=false
        \_statement=SELECT "personId" FROM "dse60"."person_p_byName" WHERE "name" = ? LIMIT ?; with params (java.
                    lang.String) Emeril Lagasse, (java.lang.Integer) 50000
        \_options=Options{consistency=Optional[ONE], serialConsistency=Optional.empty, fallbackConsistency=Option
                  al.empty, pagingState=null, pageSize=-1, user=Optional.empty, waitForSchemaAgreement=true, asyn
                  c=true}
    ...
    最初のステップDsegGraphStepで使用されるindex-queryは、インデックス・タイプをmaterializedと識別することに注意してください。インデックスが使用されなかった場合、index-queryはプロファイル出力に含まれません。
エッジ・インデックス
  • エッジ・インデックスを使用すると、クエリーを絞り込むことができます。たとえば、John Doeが書いた、評価が3つ星以上のレビューのすべての外向きエッジを検索するクエリーは、以下のようになります。
    g.V().has('person','name','John Doe').outE().has('stars', gte(3))
    クエリーでprofile()を使用すると、最初のステップでグローバル・インデックス・クエリーが使用されたことが示されます。ここに示す出力は、2番目のステップで、クエリーのレイテンシーを短縮するためにratedByStarsエッジ・インデックスが使用されたことを示しています。
    ヒント: local()ステップを使用して、エッジ・インデックスがクエリーを絞り込む方法に影響を与えることができます。
プロパティ・インデックス
  • プロパティ・インデックスを使用すると、クエリーを絞り込むことができます。たとえば、1961年以降、Julia Childが住んだことのある国(この場合、1つのみ)を検索できます。
    g.V().has('person', 'name','Julia Child').as('person').
       local(properties('country').has('startYear', 1961)).value().as('country').
       select('person','country').
          by('name').by().profile()
    gremlin> g.V().has('person', 'name','Julia Child').as('person').
    ......1>    local(properties('country').has('startYear', 1961).value()).as('country').
    ......2>    select('person','country').
    ......3>       by('name').by().profile()
    ==>Traversal Metrics
    Step                                                               Count  Traversers       Time (ms)    % Dur
    =============================================================================================================
    DsegGraphStep(vertex,[],(label = person & name ...                     1           1           1.274    37.35
      query-optimizer                                                                              0.253
        \_condition=((label = person & name = Julia Child) & (true))
      query-setup                                                                                  0.008
        \_isFitted=true
        \_isSorted=false
        \_isScan=false
      index-query                                                                                  0.557
        \_indexType=Materialized
        \_usesCache=false
        \_statement=SELECT "personId" FROM "newComp"."person_p_byName" WHERE "name" = ? LIMIT ?; with params (jav
                    a.lang.String) Julia Child, (java.lang.Integer) 50000
        \_options=Options{consistency=Optional[ONE], serialConsistency=Optional.empty, fallbackConsistency=Option
                  al.empty, pagingState=null, pageSize=-1, user=Optional.empty, waitForSchemaAgreement=true, asyn
                  c=true}
    DsegHasStep@[person]                                                   1           1           0.060     1.76
    LocalStep([DsegPropertiesStep([country],propert...                     1           1           1.300    38.12
      DsegPropertiesStep([country],property,(label ...                     1           1           1.149
        query-optimizer                                                                            0.239
        \_condition=((label = country & startYear = 1961) & (true))
        query-setup                                                                                0.001
        \_isFitted=true
        \_isSorted=false
        \_isScan=false
        vertex-query                                                                               0.564
        \_usesCache=false
        \_statement=SELECT * FROM "newComp"."person_p_OUT_byStartYear_p" WHERE "personId" = ? AND "~~property_ke
                     y_id" = ? AND "~startYear" = ? LIMIT ? ALLOW FILTERING; with params (java.lang.Integer) 1, (
                     java.lang.Integer) 32801, (java.lang.Integer) 1961, (java.lang.Integer) 50000
        \_options=Options{consistency=Optional[ONE], serialConsistency=Optional.empty, fallbackConsistency=Optio
                   nal.empty, pagingState=null, pageSize=-1, user=Optional.empty, waitForSchemaAgreement=true, as
                   ync=true}
        \_usesIndex=true
      DsegHasStep([startYear.eq(1961)])                                    1           1           0.081
      PropertyValueStep                                                    1           1           0.026
    SelectStep(last,[person, country],[value(name),...                     1           1           0.720    21.13
    NoOpBarrierStep(2500)                                                  1           1           0.032     0.95
    DsegPropertyLoadStep                                                   1           1           0.023     0.69
                                                >TOTAL                     -           -           3.411        -
    クエリーでprofile()を使用すると、最初のステップでグローバル・インデックス・クエリーが使用されたことが示されます。ここに示す出力は、2番目のSELECTステップで、クエリーのレイテンシーを短縮するためにbyStartYearプロパティ・インデックスが使用されたことを示しています。
    ヒント: プロパティ・インデックスと使用するには、local()ステップも便利です。