neo4j 如果路径不存在,则创建所有不存在的节点和边

oyt4ldly  于 2023-11-18  发布在  其他
关注(0)|答案(2)|浏览(104)

我想把Python包的模块表示为neo4j图中的节点。我得到如下输入,如果模块还没有被包含,我必须更新图。假设我的输入看起来像这样:

  1. a.b.c.d
  2. a.b.c.e
  3. a
  4. a.b.c
  5. a.b

字符串
如果a.b.c已经存在,我不想在遇到a.b.c.d时重新创建这些节点。我只想创建一个名为d的新节点并将其连接到c。同样,如果我得到a.b.c,而这些节点都不存在,然后我想创建所有的节点,并相应地连接它们。我的真实的输入可以有任意数量的节点,所以我想要一个可以处理任意路径长度的密码查询。
我是新来的。这是我第一次尝试。

  1. MERGE p=(module:Module {name: $module_name})
  2. WITH p, module
  3. MATCH (package:Module)-[:contains*]->(module)
  4. WHERE [x in nodes(p) | x.name] = $module_path


然而,Cypher给了我以下错误:
查询无法以MATCH结束
我也试过这个:

  1. MERGE p=(:Module)-[:contains*]->(:Module)
  2. WHERE [x in nodes(p) | x.name] = $module_path


但是Cypher抱怨WHERE的存在。
请注意,我使用neo4j Python库来运行这个查询,我传入了这样的参数:{"module_path":["a","b","c"], "module_name":"c"}。如果有更好的方法,我很乐意以不同的方式来参数化我的查询,但我不认为这是我错误的根源。
我用的是neo4j 5.12社区版。

kqqjbcuj

kqqjbcuj1#

您可以使用纯Cypher方法,如下所示:

  1. FOREACH (i IN range(0, size($module_path) - 2) |
  2. MERGE (l:Module {name: $module_path[i]})
  3. MERGE (r:Module {name: $module_path[i+1]})
  4. MERGE (l)-[:contains]->(r) );

字符串
你可以用问题中的数据来测试这是如何工作的:

  1. UNWIND [['a','b','c','d'],['a','b','c','e'],['a'],['a','b','c'],
  2. ['a','b']] AS modules
  3. FOREACH (i IN range(0, size(modules) - 2) |
  4. MERGE (l:Module {name: modules[i]})
  5. MERGE (r:Module {name: modules[i+1]})
  6. MERGE (l)-[:contains]->(r) )


结果如下:

展开查看全部
5cg8jx4n

5cg8jx4n2#

它可以通过以下查询实现(添加了注解)

  1. // simulate your input
  2. WITH "a.b.c.d" AS pkg
  3. // split on the dot, producing an array
  4. WITH split(pkg, ".") AS parts ['a','b','c','d']
  5. // iterating of the array
  6. UNWIND parts AS part
  7. // MERGE (match or create) the module with the name as id ( up to you which property to use )
  8. MERGE (m:Module {id: part})
  9. // break and introduce a variable being an array of the nodes created or matched
  10. WITH collect(m) AS modules
  11. // use APOC to link those nodes together with the NEXT relationship
  12. CALL apoc.nodes.link(modules,'NEXT')

字符串
它产生这样的图形


的数据
稍后,如果您尝试对已经存在的模块路径执行相同的操作,它将不会执行任何操作,例如,在执行上述操作之后,以下查询将不会创建任何内容

  1. WITH "a.b.c" AS pkg
  2. WITH split(pkg, ".") AS parts
  3. UNWIND parts AS part
  4. MERGE (m:Module {id: part})
  5. WITH collect(m) AS modules
  6. CALL apoc.nodes.link(modules,'NEXT')


展开查看全部

相关问题