Как получить все чайлды конкретного узла в neo4j


У меня есть это отношение в моем neo4j :

Parent -> Childs
F -> D,E
D -> A,B,C

Use case : я пытаюсь получить все дочерние элементы конкретного узла с помощью этого запроса

MATCH (p:Person{name:"F"})<-[:REPORTS_TO*]-(c) 
RETURN {parent : p.name, child : {name :collect( c.name)}}

Это возвращает мне следующее:

{"parent":"F","child":{"name":["D","A","B","C","E"]}}

A, B, C не являются прямым потомком F, поскольку они являются потомком D

Требуется ответ

[
"F" : [ Childs i.e "E", "D" ]
"E" : []
"D" : [ "A", "B", "C" ]
 and so on ....
]

Один из способов достичь этого-запустить этот ниже запрос рекурсивно:

MATCH (p:Person{name:"F"})<-[:REPORTS_TO]-(c) 
RETURN {parent : p.name, child : {name :collect( c.name)}}

Который возвращает

{"parent":"F","child":{"name":["E","D"]}}

Затем найдите все Чайлдс из E and D , а затем Чайлдс из Чайлдса и так далее..

Мой вопрос заключается в том, Могу ли я достичь этого одним запросом или более эффективным способом?

Edit1 : добавление набора данных

CREATE (f:Person {name: "F"})
CREATE (e:Person {name: "E"})
CREATE (d:Person {name: "D"})
CREATE (c:Person {name: "C"})
CREATE (b:Person {name: "B"})
CREATE (a:Person {name: "A"})
CREATE (x:Person {name: "X"})
CREATE (a)-[:REPORTS_TO]->(x)
CREATE (d)-[:REPORTS_TO]->(a)
CREATE (d)-[:REPORTS_TO]->(b)
CREATE (d)-[:REPORTS_TO]->(c)
CREATE (f)-[:REPORTS_TO]->(d)
CREATE (f)-[:REPORTS_TO]->(e)
2 3

2 ответа:

Вы можете использовать необязательный матч для достижения своей цели.

Ваш набор данных выглядит следующим образом:

Набор данных

Попробуйте:

MATCH (p:Person)
OPTIONAL MATCH (p)<-[:REPORTS_TO]-(c) 
RETURN {parent : p.name, child : {name :collect( c.name)}}

Результаты запроса:

+-----------------------------------------------------+
| {parent : p.name, child : {name :collect( c.name)}} |
+-----------------------------------------------------+
| {parent=D, child={name=[C, B, A]}}                  |
| {parent=A, child={name=[]}}                         |
| {parent=C, child={name=[]}}                         |
| {parent=F, child={name=[E, D]}}                     |
| {parent=E, child={name=[]}}                         |
| {parent=B, child={name=[]}}                         |
+-----------------------------------------------------+

Если вам нужен только конкретный родитель и ваши соответствующие дети, вы можете сделать:

MATCH (p:Person)
WHERE p.name = "D"
OPTIONAL MATCH (p)<-[:REPORTS_TO]-(c) 
WITH COLLECT (c) + p AS all
UNWIND all as p
MATCH (p)
OPTIONAL MATCH (p)<-[:REPORTS_TO]-(c) 
RETURN {parent : p.name, child : {name :collect( c.name)}}

В результате:

+-----------------------------------------------------+
| {parent : p.name, child : {name :collect( c.name)}} |
+-----------------------------------------------------+
| {parent=D, child={name=[C, B, A]}}                  |
| {parent=A, child={name=[]}}                         |
| {parent=C, child={name=[]}}                         |
| {parent=B, child={name=[]}}                         |
+-----------------------------------------------------+

Редактировать:

Из комментария @Prakash Pandey:

Как мы можем сделать что-то вроде Чайлдс, Чайлдс из Чайлдс и так далее, где p.name = " Том "

Основываясь на наборе данных, добавленном в вопрос, вы можете сделать:

MATCH (p:Person)<-[:REPORTS_TO*]-(c:Person)
WHERE p.name = "X"
WITH COLLECT (c) + p AS all UNWIND all as p
MATCH (p)<-[:REPORTS_TO]-(c)
RETURN {parent : p.name, child : {name :collect( c.name)}}

Результат:

+-----------------------------------------------------+
| {parent : p.name, child : {name :collect( c.name)}} |
+-----------------------------------------------------+
| {parent=D, child={name=[F]}}                        |
| {parent=A, child={name=[D]}}                        |
| {parent=X, child={name=[A]}}                        |
+-----------------------------------------------------+

Я создал график, который вы описываете.

Следующий запрос возвращает большую часть того, что вам нужно:

MATCH (a:Parent)<-[r:isParent*0..]-(b:Parent)
return {parent:a.name,child : {name :collect( b.name)}}

Результат:

{"родитель": "D", "ребенок": {"имя": ["D","A", "B", "C"]}}

{"родитель": "а", "ребенок": {"имя": ["а"]}}

{"родитель": "C", "ребенок": {"имя": ["C"]}}

{"родитель": "F", "ребенок": {"имя": ["F", "D", "E", "A", "B", "C"]}}

{"родитель": "Е", "ребенок": {"имя": ["Е"]}}

{"родитель": "B", "ребенок": {"имя": ["B"]}}