我正在寻找一种检索所有连接节点的高性能方法。 但是有一个转折。我想排除通过某些关系类型连接的节点和子节点。
附图说明了我的情况。
有两个或多个节点簇。我想检索单个群集的所有节点,具体取决于查询中的ID。 不包括通过“ LINK ...”关系连接的所有其他节点(来自不同群集)。
我知道如何通过以下方式检索所有连接的节点:
MATCH (n:MyNode {id : 123})-[*]-(connectedNodes)
RETURN connectedNodes
使用WHERE
子句进行过滤听起来像是一个坏主意,因为它仍将获取整个图形。 APOC程序中是否有某些东西可以让我以这种方式做某事?非常感谢您的帮助。
编辑1:沙发手我尝试了注释中给出的第一个建议,但是执行时间不够。毕竟,我将尝试限制关联和节点类型。我也尝试了使用递归函数在Python中自定义实现。尚未完成。
编辑2:@InverseFalcon的建议很奏效。首先过滤一次将不考虑的所有可用关系类型,然后对相应的起始节点和有效关系类型应用apoc.path.subgraphNodes
过程。谢谢。
答案 0 :(得分:2)
Tezra的答案很不错,您将需要返回DISTINCT connectedNodes,否则将得到重复的副本,但是在高度连接的图上,这可能需要一段时间(甚至挂起),具体取决于节点的数量,因为Cypher对所有可能的比赛路径都感兴趣,而且很快就会失去控制。
对于APOC,我们可以处理这种情况,但是正如Tezra所说,我们没有办法将关系列入黑名单,即使有,我们也没有办法根据关系类型的部分名称将其列入黑名单
您需要使用的方法是首先获取所有关系类型,然后删除以LINK
开头的所有关系类型,然后将其余关系列表加入到|
分隔的字符串中。然后,您可以将其传递给关系过滤器。
CALL db.relationshipTypes() YIELD relationshipType
WHERE NOT relationshipType STARTS WITH 'LINK'
WITH collect(relationshipType) as relTypes
WITH apoc.text.join(relTypes, '|') as relTypesString
MATCH (n:MyNode {id : 123})
CALL apoc.path.subgraphNodes(n, {relationshipFilter:relTypesString}) YIELD node
RETURN node as connectedNode
答案 1 :(得分:1)
首先,我想强调的是Cypher并不限制信息的检索方式,它仅确定返回的信息。因此,在排除此问题之前,请尝试使用WHERE(此外,请尝试升级到最新的Neo4j,以获得最聪明的密码计划者)。这应该可以正常工作,因为密码计划器可以在匹配结果时过滤结果。
MATCH (n:MyNode {id : 123})-[rs*]-(connectedNodes)
WHERE NONE(r in rs WHERE TYPE(r)="LINK")
RETURN DISTINCT connectedNodes
我可以想到的APOC过程要求您命名所使用的关系(可以将标签列入黑名单,但似乎不适用于关系类型),因此与{{1} }