我这些天一直在使用索引,我注意到如果我在dmdid
上创建了一个索引键,则以下查询很快:
graph.query().has("firstname", "Joan").has("lastname", "Dupont").vertices()
这个也很快:
new GremlinPipeline(graph.getVertices("firstname", "Joan")).has("lastname", "Dupont").cast(classOf[Vertex]).toList()
但是这个很慢,好像我没有索引:
new GremlinPipeline(graph.getVertices()).has("firstname", "Joan").has("lastname", "Dupont").cast(classOf[Vertex]).toList()
我认为我的问题分为两部分(或3部分):
答案 0 :(得分:2)
我认为您的上一个查询不支持优化。挑选你的问题:
new GremlinPipeline(graph.getVertices()).has("dmdid", id).has("type", type).cast(classOf[Vertex]).toList()
您正在将图表中的所有顶点输入到管道中,然后将它们迭代到您的索引所在的has
。因此,从has
开始的管道的其余部分将其视为线性扫描。 Gremlin无法正确编译查询,因为它不了解整个事情。
您可以对索引执行的操作与底层图形密切相关。图表实现说明了优化将如何发生。关于,
首先,优化查询起始顶点的能力似乎如此 如果我必须过滤2索引键(这里首先和 姓氏)?
在蓝图意义上使用键索引获取“开始顶点”,通用方法是创建一个将名字和姓氏组合到一个属性的复合键。关于,
其次,通过管道优化遍历图表的能力似乎不起作用?
您没有说明您正在使用的图形数据库,但并非所有图形都支持将has
操作推送到数据库。 Titan尽最大努力利用这些东西,并将利用vertex centric indices在gremlin表达中找到它们的任何地方。关于:
这两个第一个概念似乎完全分开,尽管它们 似乎面临着同样的问题。让我获得所有顶点和过滤 在他们(最后一个例子)应该与2个第一个相同 因为查询是在DB上执行的,你不这么认为吗?
正如您可能从我之前的声明中收集的那样,您的查询不会在数据库上执行。 Gremlin不会编译为每个图形数据库都能理解并可以优化的表达式。 Gremlin是在Blueprints上运行的groovy代码。一些图形数据库(如Titan和OrientDB在某种程度上)能够根据其实现优化遍历。正如我上面提到的,Titan将利用顶点中心索引尽可能限制Gremlin在内存中处理的数据。这种优化可以带来好performance improvements。