Neo4j / Cypher:仅当节点与一个或多个其他节点

时间:2018-06-11 19:43:02

标签: neo4j cypher

我正在尝试构建此查询时遇到一些麻烦。我在互联网上看了很多地方,我似乎无法找到答案,所以我在这里问。

所以这是我的架构有点像。 (抱歉肮脏的油漆图)

enter image description here

我想要的查询是;

从一个Route节点开始,我得到多个RS,并从每个RS

获得一个OMS

我想找到最终连接到相同(或更多)OMS节点的所有Route节点

这是我当前的查询:

MATCH (st)--(rs:RS)--(oms:OMS)
WHERE id(st) = 0
with st,rs, oms, collect(oms) as omsn

MATCH (ed:Route)--(rs2:RS)
WHERE ALL(x in omsn WHERE (ed)--(rs2)--(x))

RETURN *

然后又回来了。

enter image description here

这几乎是正确的,但请注意,Route节点21没有连接到BOTH OMS 4和2所以我不想要那条链

结果应该是这样的。

enter image description here

如何更改查询以完成此操作? (请注意,中间的RS节点对于我正在做的其他一些事情是必要的,所以我不能删除它们。我已经让它工作了,虽然只有2层heiarchy,但这不是我需要的。)< / p>

编辑:简单插入查询

CREATE (a:Route)-[:rel]->(b:RS)-[:rel]->(c:OMS)

CREATE (a)-[:rel]->(d:RS)-[:rel]->(e:OMS)

CREATE (f:Route)-[:rel]->(g:RS)-[:rel]->(c)
CREATE (f)-[:rel]->(i:RS)-[:rel]->(e)
CREATE (f)-[:rel]->(k:RS)-[:rel]->(hfg:OMS)

CREATE (l:Route)-[:rel]->(m:RS)-[:rel]->(c)
CREATE (l)-[:rel]->(o:RS)-[:rel]->(e)
CREATE (l)-[:rel]->(asd:RS)-[:rel]->(dsf:OMS)
CREATE (l)-[:rel]->(ds:RS)-[:rel]->(gdg:OMS)

MATCH (m:OMS) WHERE id(m) = 4
CREATE (:Route)-[:rel]->(:RS)-[:rel]->(m)

RETURN *

1 个答案:

答案 0 :(得分:1)

使用Cypher的2个技巧。

1)在每个RETURN *之后使用WITH运行测试,以验证您是否返回了所需内容。

2)查看文本表以验证返回数据的格式。

您的查询存在的问题是此部分

MATCH (st)--(rs:RS)--(oms:OMS)
WHERE id(st) = 0
with st,rs, oms, collect(oms) as omsn
  • (st)是单个节点,因此是1行数据
  • (rs)是两个不同的节点,所以现在有2行数据
  • 每个(oms)节点是(rs)节点之外的一个节点。因此每个(rs)为1行。
  • RETURN *将返回1 * 2 * COLLECT(1)为1 = 2行
    • 请注意,您有2行数据,每行包含1个不同的(oms)节点

这里的解决方案是

  • 在WITH中使用COLLECT(rs)将这2行折叠为1,这样2(oms)节点也会被收集到同一个列表中(注意,这可能包含重复的oms节点。使用COLLECT(DISTINCT oms)如果这将是一个问题)
  • 仅在WITH部分中携带COLLECT(oms)。其余的将在以下比赛中再次匹配。

最后的说明。你知道关系的方向;将其包含在Cypher中以获得更好/更清洁的性能。