需要帮助并想知道我们如何将这种类型的 Neo4j Cypher 查询写入 Gremlin 查询?
Need help and Want to know how we can write this type of Neo4j Cypher query into Gremlin query?
MATCH (m:movie)-[has_directed_by:has_directed]->(director:Director)
OPTIONAL MATCH(director)-[has_name:has_name]->(directorName:DirectorName)
OPTIONAL MATCH(director)-[has_type:has_type]->(directionType:DirectionType)
OPTIONAL MATCH(director)-[has_language:has_language]->(directionLanguage:DirectionLangugaue)
OPTIONAL MATCH (director)-[has_script:has_script]->(script:Script)
OPTIONAL MATCH (m)-[has_songs:has_songs]->(songs:Songs)
WITH m,has_directed_by,director,has_name,directorName,has_type,directionType,
has_language,directionLanguage,has_script,script order by m.id ASC
RETURN distinct m,collect(has_directed_by),collect(director),collect(has_name),
collect(directorName),collect(has_type),collect(directionType),collect(has_language),collect(directionLanguage),collect(has_script),collect(script),collect(has_songs),collect(songs);
如何在密码中为这种类型的硬查询编写一个 gremlin 查询?
请帮忙!我想知道我们如何在 gremlin 中一次又一次地引用 'm' 和 'director'。
示例:
g.V().
hasLabel('movie').as('m').
outE('has_directed').
inV().
hasLabel('Director').as('director')
但是在接下来的图遍历中需要参考那个'm'和'director'。请帮助
所以,没有双关语的意思,对于像这样的转换,最好一次采取一个步骤。第一行大致相当于:
g.V().
hasLabel('movie').as('m').
outE('has_directed').
inV().
hasLabel('Director').as('director')
但是,通常可以使用更惯用的 Gremlin,它可以使用围绕 project
等步骤构建的方法来避免大量 as
步骤。如果您需要从边缘检索属性,则只需要 outE
和 inV
步骤。否则只需 out
就足够了。
Gremlin 也有一个 match
步骤,可让您以类似的声明式样式转换 Cypher 查询,但我更喜欢使用其他 Gremlin 步骤并在大多数情况下避免 match
。
在 Gremlin 中有一个 optional
步骤,但也有 coalesce
和 choose
步骤允许您编写一种 IF...THEN...ELSE
类型的查询相当于 OPTIONAL MATCH
就 distinct
而言,等效的 Gremlin 步骤是 dedup
在 Gremlin 中将可选内容组合在一起的一种方法是使用 union
步骤。
Gremlin 中的 fold
步骤的使用方式与 Cypher 中的 collect
步骤类似。
因为我没有你的数据集,所以我使用 air-routes 数据集来演示 OPTIONAL MATCH
的等价物,本质上是使用 fold
步骤生成一个空列表没有结果。
gremlin> g.V('0','44').
......1> project('start','neighbors').
......2> by(id).
......3> by(out().fold())
==>[start:0,neighbors:[]]
==>[start:44,neighbors:[v[8],v[13],v[20],v[31]]]
如上所述,fold
步骤类似于 Cypher collect
函数。在上面的示例中,当没有匹配项时,邻居由一个空列表表示。您可以根据需要为 project
步骤拥有尽可能多的子部分(键名和 by
调制器)来表示所有可选案例。
当然有很多方法可以编写查询,具体取决于您希望如何表示未找到任何内容的情况。如果您更喜欢使用默认值而不是空列表,则可以使用 coalesce
步骤。
gremlin> g.V('0','44').
......1> project('start','neighbors').
......2> by(id).
......3> by(coalesce(out(),constant('None')))
==>[start:0,neighbors:None]
==>[start:44,neighbors:v[8]]
对您的数据集使用类似的模式,基本构建块可能是:
g.V().
hasLabel('Movie').
project('movie','director').
by(valueMap().with(WithOptions.tokens)).
by(out('has_directed').valueMap().with(WithOptions.tokens).fold())
valueMap
步骤将 return 顶点(或边)的所有属性。我将其添加到我的示例中以模拟 Cypher 将执行的操作。默认情况下(没有像 valueMap
这样的步骤)Gremlin 在许多情况下只会 return 没有其属性的顶点。 with
告诉 Gremlin 在结果中也包含 ID 和标签。这等同于弃用的形式 valueMap(true)
.
MATCH (m:movie)-[has_directed_by:has_directed]->(director:Director)
OPTIONAL MATCH(director)-[has_name:has_name]->(directorName:DirectorName)
OPTIONAL MATCH(director)-[has_type:has_type]->(directionType:DirectionType)
OPTIONAL MATCH(director)-[has_language:has_language]->(directionLanguage:DirectionLangugaue)
OPTIONAL MATCH (director)-[has_script:has_script]->(script:Script)
OPTIONAL MATCH (m)-[has_songs:has_songs]->(songs:Songs)
WITH m,has_directed_by,director,has_name,directorName,has_type,directionType,
has_language,directionLanguage,has_script,script order by m.id ASC
RETURN distinct m,collect(has_directed_by),collect(director),collect(has_name),
collect(directorName),collect(has_type),collect(directionType),collect(has_language),collect(directionLanguage),collect(has_script),collect(script),collect(has_songs),collect(songs);
如何在密码中为这种类型的硬查询编写一个 gremlin 查询? 请帮忙!我想知道我们如何在 gremlin 中一次又一次地引用 'm' 和 'director'。
示例:
g.V().
hasLabel('movie').as('m').
outE('has_directed').
inV().
hasLabel('Director').as('director')
但是在接下来的图遍历中需要参考那个'm'和'director'。请帮助
所以,没有双关语的意思,对于像这样的转换,最好一次采取一个步骤。第一行大致相当于:
g.V().
hasLabel('movie').as('m').
outE('has_directed').
inV().
hasLabel('Director').as('director')
但是,通常可以使用更惯用的 Gremlin,它可以使用围绕 project
等步骤构建的方法来避免大量 as
步骤。如果您需要从边缘检索属性,则只需要 outE
和 inV
步骤。否则只需 out
就足够了。
Gremlin 也有一个 match
步骤,可让您以类似的声明式样式转换 Cypher 查询,但我更喜欢使用其他 Gremlin 步骤并在大多数情况下避免 match
。
在 Gremlin 中有一个 optional
步骤,但也有 coalesce
和 choose
步骤允许您编写一种 IF...THEN...ELSE
类型的查询相当于 OPTIONAL MATCH
就 distinct
而言,等效的 Gremlin 步骤是 dedup
在 Gremlin 中将可选内容组合在一起的一种方法是使用 union
步骤。
Gremlin 中的 fold
步骤的使用方式与 Cypher 中的 collect
步骤类似。
因为我没有你的数据集,所以我使用 air-routes 数据集来演示 OPTIONAL MATCH
的等价物,本质上是使用 fold
步骤生成一个空列表没有结果。
gremlin> g.V('0','44').
......1> project('start','neighbors').
......2> by(id).
......3> by(out().fold())
==>[start:0,neighbors:[]]
==>[start:44,neighbors:[v[8],v[13],v[20],v[31]]]
如上所述,fold
步骤类似于 Cypher collect
函数。在上面的示例中,当没有匹配项时,邻居由一个空列表表示。您可以根据需要为 project
步骤拥有尽可能多的子部分(键名和 by
调制器)来表示所有可选案例。
当然有很多方法可以编写查询,具体取决于您希望如何表示未找到任何内容的情况。如果您更喜欢使用默认值而不是空列表,则可以使用 coalesce
步骤。
gremlin> g.V('0','44').
......1> project('start','neighbors').
......2> by(id).
......3> by(coalesce(out(),constant('None')))
==>[start:0,neighbors:None]
==>[start:44,neighbors:v[8]]
对您的数据集使用类似的模式,基本构建块可能是:
g.V().
hasLabel('Movie').
project('movie','director').
by(valueMap().with(WithOptions.tokens)).
by(out('has_directed').valueMap().with(WithOptions.tokens).fold())
valueMap
步骤将 return 顶点(或边)的所有属性。我将其添加到我的示例中以模拟 Cypher 将执行的操作。默认情况下(没有像 valueMap
这样的步骤)Gremlin 在许多情况下只会 return 没有其属性的顶点。 with
告诉 Gremlin 在结果中也包含 ID 和标签。这等同于弃用的形式 valueMap(true)
.