Search code examples
databaseneo4jcyphergraph-databases

Neo4j query multiple hops


Hi guys I am trying to write a neo4j query to get multiple hops.

Currently my schema is authors - fname,lname & paper - title

relationship: author -> WROTE -> paper

MATCH (a:Author)-[:WROTE]->(p:Paper)
WITH a as auth1, count(p.title) as count1
MATCH (auth1) -[:WROTE *1]->(p2:Paper),
              (auth2)-[:WROTE *1]->(p2)
WHERE count1 > 7
RETURN DISTINCT auth1.fname, auth1.lname, auth2.fname,  auth2.lname

What I am trying to do is find everyone connected to my author who has the most papers authored - for starters 1 hop, then 2 hops etc. I know the author with the most papers has 8 written thus why my count > 7; however I don't think my query is right. Whenever I change

:WROTE *1 to :WROTE *1..2

the results are the same which I believe they shouldn't be - any help would be appreciated


Solution

  • [EDITED]

    Below is a query that does not need to know beforehand how many papers your most productive author (co)wrote. It automatically determines who that author is, and then finds all of his/her co-authors and their co-authors. For this to work, the -[:WROTE*..3]- pattern is nondirectional and uses an upper bound of 3 (since there would be a hop of 3 relationships to get to the coauthors of the coauthors). In general, if you want coauthors to a depth of N, you need an upper bound of (1+(N-1)*2).

    MATCH (auth1:Author)-[:WROTE]->(p:Paper)
    WITH auth1, COUNT(p) AS count1
    ORDER BY count1 DESC LIMIT 1
    MATCH (auth1)-[:WROTE]->(:Paper)-[:WROTE*..3]-(auth2:Author)
    RETURN DISTINCT auth1.fname, auth1.lname, auth2.fname,  auth2.lname;
    

    In addition, if you want to visualize in the neo4j Browser all the co-authors of interest and their co-written papers, this should work:

    MATCH (auth1:Author)-[:WROTE]->(p:Paper)
    WITH auth1, COUNT(p) AS count1
    ORDER BY count1 DESC LIMIT 1
    MATCH path=(auth1)-[:WROTE]->(:Paper)-[:WROTE*..3]-(auth2:Author)
    WITH auth1, auth2, NODES(path) AS ns
    RETURN DISTINCT auth1, auth2, [i IN RANGE(1, SIZE(ns)-1, 2) | ns[i]] AS papers
    

    RANGE(1, SIZE(ns)-1, 2) returns a list of the indexes of the Paper nodes in each path (since they have the odd indexes).

    Make sure to disable the Connect result nodes option in Browser Settings, or else the visualization may show extra nodes that are not in the results.