Neo4j / Cypher: сопоставлять узлы, только если они имеют отношение с 1 или более другими узлами - PullRequest
0 голосов
/ 11 июня 2018

У меня возникли проблемы с этим запросом, который я пытаюсь построить.Я просмотрел множество мест в Интернете и, похоже, не смог найти ответ, поэтому я спрашиваю здесь.

, вот как выглядит моя схема.(извините за дерьмовую диаграмму рисования)

enter image description here

Я хочу запрос:

Начиная с одного узла маршрута, я получаю несколько RSи одну OMS от каждого RS

Я хочу найти все узлы Route, которые в конечном итоге подключаются к тем же (или более) узлам OMS

, вот мой текущий запрос:

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

Это почти правильно, но обратите внимание, что узел 21 маршрута не подключается к ОБА OMS 4 и 2, поэтому я НЕ хочу эту цепь

Результат должен быть примерно таким:

enter image description here

Как бы я изменил свой запрос, чтобы выполнить это вместо этого?(Обратите внимание, что узел RS в середине необходим для некоторых других вещей, которые я также делаю, поэтому я не могу удалить их. Я получил его работу, хотя только с двухслойной иерархией, но это не то, что мне нужно.)

редактировать: простой запрос вставки

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 голосов
/ 11 июня 2018

2 совета по работе с Cypher.

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).Таким образом, 1 строка для каждого (rs).
  • RETURN * вернет 1 * 2 * COLLECT (1) как 1 = 2 строки
    • Обратите внимание, что у вас есть 2 строки данных, каждая с1 отдельный (oms) узел

Решение здесь состоит в том, чтобы либо сделать

  • Использовать COLLECT (rs) в WITH, чтобы свернуть эти 2 строкив 1, так что 2 (oms) узла также собираются в один и тот же список (обратите внимание, что это может содержать дубликаты oms-узлов. Используйте COLLECT (DISTINCT oms), если это будет проблемой)
  • Только переносСОБРАТЬ (oms) в части СО.Остальные будут сопоставлены снова в следующем матче в любом случае.

Заключительная нота.Вы знаете направление отношений;Включите его в Cypher для лучшей / более чистой производительности.

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