neo4j Cypher - пройти путь переменной длины, но остановиться, когда метка найдена - PullRequest
1 голос
/ 10 апреля 2020

Предположим, что моя база данных графа имеет "поток" из foo узлов. между foo узлами может быть любое количество bar, bar1, bar2, ... barN узлов, которые в конечном итоге подключаются к следующему foo узлу.

Итак, все это возможно

  • (a: foo) -> (: bar) -> (b: foo)
  • (b: foo ) -> (: bar) -> (c: foo) -> (: bar1) -> (d: foo)
  • (a: foo) -> (: bar ) -> (: bar1) -> (: bar2) -> (: barN) -> (c: foo)

et c.

Я хотел бы вернуть каждую отдельную пару foo узлов, которые НЕ имеют других foo узлов между ними

Для приведенных выше примеров решение должно вернуть:

  • а, б
  • б, c
  • c, д
  • а, c

Решение НЕ должно включать следующее, между которыми есть узлы foo:

  • b, d
  • a, d

Что я пробовал это возвращает все пары foo, которые соединяются, независимо от того, что находится между ними.

MATCH x=(a:foo)-[:RELTYPE*1..]->(b:foo)
RETURN a,b

Ответы [ 2 ]

1 голос
/ 10 апреля 2020

Это должно работать:

MATCH x = (a:foo)-[:RELTYPE*..]->(b:foo)
WHERE NONE(n IN NODES(x)[1..-1] WHERE ANY(l IN LABELS(n) WHERE l = 'foo'))
RETURN a, b

[ОБНОВЛЕНИЕ]

Или даже лучше:

MATCH x = (a:foo)-[:RELTYPE*..]->(b:foo)
WHERE NONE(n IN NODES(x)[1..-1] WHERE n:foo)
RETURN a, b
0 голосов
/ 11 апреля 2020

Вы также можете использовать APO C Процедуры для процедур расширения пути , которые могут обрабатывать этот тип использования.

Используя этот график:

CREATE (a:foo {name:'a'}), (b:foo {name:'b'}), (c:foo {name:'c'}), (d:foo {name:'d'}), 
(a)-[:RELTYPE]->(:bar)-[:RELTYPE]->(b), 
(b)-[:RELTYPE]->(:bar)-[:RELTYPE]->(c)-[:RELTYPE]->(:bar1)-[:RELTYPE]->(d), 
(a)-[:RELTYPE]->(:bar)-[:RELTYPE]->(:bar1)-[:RELTYPE]->(:bar2)-[:RELTYPE]->(:barN)-[:RELTYPE]->(c)

Мы можем применить этот запрос:

MATCH (start:foo)
CALL apoc.path.subgraphNodes(start, {relationshipFilter:'RELTYPE>', labelFilter:'/foo'}) YIELD node as end
RETURN start, end

Он начинается на каждом узле: foo, пересекает только исходящие отношения: RELTYPE и прекращает расширение при достижении узла: foo с пометкой (/ перед 'foo 'в фильтре меток указывает, что это фильтр завершения на метке).

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...