Variable path queries


(Rcfro2) #1

With variable path query such as the following:

match path = (t:Person{name:"Tom Hanks"})-[:KNOWS*2..5]-(fof)
where not (t)-[:KNOWS]-(fof)
return path, length(p) as Length

Does it protect for all steps in-between 2 to 5 node hops away? In other words, does this also ensure that 2,3,4,5 node hops away, (fof) does not know (t)? IN addition, is it also the case that necessarily none of those node hops can also be Tom Hanks as the query only follows the path from Tom Hanks ?


(Andrew Bowman) #2

The WHERE clause only applies to fof, so while it will hold true for any fof node, it will not necessarily apply to nodes earlier in the path.

For example, if there is an fof node that is 5 hops away from Tom Hanks where fof doesn't know Tom, any of the previous hops on that path may be to people who do know Tom. If you had a requirement where all nodes in the path (or even a segment of that path) had to also not know Tom Hanks, then you'd need to explicitly add that to your query, such as with something like this:

WHERE none(node in nodes(path)[2..5] WHERE (t)-[:KNOWS]-(node))

It's entirely possible for Tom Hanks to appear multiple times in the path, but we know for certain that they can't be the second or third node in the path (unless Tom :KNOWS himself or there are multiple :KNOWS relationships between Tom and a person).

The restriction in Cypher pattern matching is that for a single MATCH, a relationship can only be traversed once per path (so we can't traverse a :KNOWS relationship from Tom and then reuse the same relationship to get back to Tom, for example).

If you need stronger restrictions, such as never revisiting a node per path, then you'll need a different approach, either specifying this in a more complex predicate, or using something like APOC path expander procedures, which can allow you to specify the uniqueness constraints used during expansion.