Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Gremlin graph traversal that uses previous edge property value to filter later edges

In a graph traversal I only want to consider edges that have a property that is equal to the property of one of the edges visited in a previous step in the traversal.

I found http://tinkerpop.apache.org/docs/current/recipes/#traversal-induced-values but this appears to only work for a single object, in my case I need the value to change as I traverse. For example starting at V1 that has the outbound edges (E1, E2, E3...) I want to traverse out E1 to V2 and then traverse along any edge from V2 where edge.property(x) == E1.property(x), and do the same for all edges out of V1 (E2, E3, ...)

I can't find any documentation that supports a way to do this in Gremlin, is it possible?

like image 391
Chris Reeves Avatar asked Oct 20 '16 22:10

Chris Reeves


1 Answers

We can use the modern toy graph that ships with TinkerPop:

gremlin> graph = TinkerFactory.createModern()
==>tinkergraph[vertices:6 edges:6]
gremlin> g = graph.traversal()
==>graphtraversalsource[tinkergraph[vertices:6 edges:6], standard]

This graph already contains 6 edges of which two have a weight of 1.0:

gremlin> g.E().valueMap()
==>[weight:0.5]
==>[weight:1.0]
==>[weight:0.4]
==>[weight:1.0]
==>[weight:0.4]
==>[weight:0.2]

We use one of these two edges with a weight of 1.0 to get the other edge with the same weight. By traversing the first of these two edges, we land at a vertex that has two outgoing edges:

gremlin> g.V(1).outE().has('weight',1.0).inV().outE()
==>e[10][4-created->5]
==>e[11][4-created->3]
gremlin> g.V(1).outE().has('weight',1.0).inV().outE().valueMap()
==>[weight:1.0]
==>[weight:0.4]

One of these edges is the other one with the weight of 1.0. So, we only have to filter these edges based on the weight of the first edge:

gremlin> g.V(1).outE().has('weight',1.0).
                as('firstEdge'). // save the first edge
                inV().outE().
                where(eq('firstEdge')). // compare with the first edge
                by('weight') // use only the 'weight' property for the equality check
==>e[10][4-created->5]
like image 84
Florian Hockmann Avatar answered Oct 13 '22 01:10

Florian Hockmann