2

I'm struggling with a problem despite having read a lot of documentation... I'm trying to find my graph root node (or nodes, they may be several top nodes) and counting their immediate children (all relations are typed :BELONGS_TO)

My graph looks like this (cf. attached screenshot). I have been trying the following query which works as long as the root node only has ONE incomming relationship, and it doesn not when it has more than one. (i'm not realy familiar with the cyhper language yet).

MATCH (n:Somelabel) WHERE NOT (()-[:BELONGS_TO]->(n:Somelabel)) RETURN n

Any help would be much appreciated ! (i haven't even tried to count the root nodes immediate children yet...which would be "2" according to my graph)

enter image description here

Correct query was given by cybersam

MATCH (n:Somelabel) WHERE NOT (n)-[:BELONGS_TO]->() RETURN n;

MATCH (n:Somelabel)<-[:BELONGS_TO]-(c:Somelabel)
WHERE NOT (n)-[:BELONGS_TO]->() RETURN n, count(c);
Romain Bruckert
  • 2,546
  • 31
  • 50

1 Answers1

4

Based on your diagram, it looks like you are actually looking for "leaf" nodes. This query will search for all Somelabel nodes that have no outgoing relationships, and return each such node along with a count of the number of distinct nodes that have a relationship pointing to that node.

MATCH (n:Somelabel)
WHERE NOT (n)-[:BELONGS_TO]->()
OPTIONAL MATCH (m)-[:BELONGS_TO]->(n)
RETURN n, COUNT(DISTINCT m);

If you are actually looking for all "root" nodes, your original query would have worked.

As a sanity check, if you have a specific node that you believe is a "leaf" node (let's say it has an id value of 123), this query should return a single row with null values for r and m. If you get non-null results, then you actually have outgoing relationships.

MATCH (n {id:123})
OPTIONAL MATCH (n)-[r]->(m)
RETURN r, m
cybersam
  • 63,203
  • 6
  • 53
  • 76
  • Actually i am trying to find all leaf nodes (the ones that don't have outgoing relationships). The "BELONGS_TO go me confused. Still, the queries don"t return my node... – Romain Bruckert Feb 10 '15 at 19:06
  • I've added the `:BELONGS_TO` relationship type to my answer, since you may actually have other types of relationships (that start at your "leaf" nodes). Also, are your sure that you are using the right label for your nodes? – cybersam Feb 10 '15 at 19:10
  • Thanks for that. Yep i'm using the right label ;-). Still not working. I'm wondering, that leaf node i'm trying to find might have other outgoing relationships that i don't see in the Neo4j browser... could that be ? How could i list all the relationship from/out that node (by {id:"sssss"} to find out ? One last thing. The leaf node has several incoming relationships. would you query work even though ? – Romain Bruckert Feb 10 '15 at 19:15
  • PS: MATCH (n:Somelabel) WHERE NOT (n)<-[:BELONGS_TO]-() RETURN n for finding the root nodes actually works – Romain Bruckert Feb 10 '15 at 19:18
  • But that is the way to find "root" nodes! – cybersam Feb 10 '15 at 19:19
  • Wait, i'm confused if i'm trying to find the root or leaf... i'm trying to find the one that has NO OUTGOING relationship ! ;-) – Romain Bruckert Feb 10 '15 at 19:24
  • Then you are trying to find the "leaf" nodes. Your last query was for root nodes. – cybersam Feb 10 '15 at 19:25
  • I've added a sanity check step to my answer. – cybersam Feb 10 '15 at 20:05
  • Thanks. I made it work ! you first query was right : MATCH (n:Somelabel) WHERE NOT (n)-[:BELONGS_TO]->() RETURN n Would you have an idea to count the immediate children in the same query ? – Romain Bruckert Feb 10 '15 at 23:23
  • See my updated answer for how to get the leaf nodes and the number of distinct "parents" for each one. – cybersam Feb 10 '15 at 23:43