2

I have the graph as shown in the figure below. The numbers represent the level format of the node which is required as output from the gremlin query along with the properties of the nodes. The graph structure can change that is more nodes can be added to the graph. The level must be returned in a similar format for additional nodes. For example, children of 1.1.1 should return the level as 1.1.1.1,1.1.1.2 ... The following query but the level is in continuous format 1,2,3 ...

g.withSack(0).
  V().
  hasLabel('A').
  has('label_A','A').
  emit().
  repeat(sack(sum).by(constant(1)).out()).
    project('depth', 'properties').
      by(sack()).
      by(valueMap())

A is starting root node.

I know its too complicated. If not possible can we at least get the sub depth along with depth using multiple sack variables. Following is the example:

depth:0 sub-depth:0 depth:1 sub-depth:1.1 depth:1 sub-depth:1.2 depth:2 sub-depth:2.1 depth:2 sub-depth:2.2 depth:2 sub-depth:2.3 depth:2 sub-depth:2.4 enter image description here

Phoenix
  • 181
  • 2
  • 9
  • Is it possible to modify the above query to get the output at least as follows: depth:0 sub-depth:0 depth:1 sub-depth:1.1 depth:1 sub-depth:1.2 depth:2 sub-depth:2.1 depth:2 sub-depth:2.2 depth:2 sub-depth:2.3 depth:2 sub-depth:2.4 – Phoenix Jun 11 '20 at 08:57

1 Answers1

2

A simple way to do what you are looking for is to take advantage of the index step. If we create a simple binary tree as follows:

g.addV('root').property('data',9).as('root').   
  addV('node').property('data',5).as('b').   
  addV('node').property('data',2).as('c').   
  addV('node').property('data',11).as('d').   
  addV('node').property('data',15).as('e').   
  addV('node').property('data',10).as('f').   
  addV('node').property('data',1).as('g').   
  addV('node').property('data',8).as('h').   
  addV('node').property('data',22).as('i').   
  addV('node').property('data',16).as('j').   
  addE('left').from('root').to('b').
  addE('left').from('b').to('c').
  addE('right').from('root').to('d').
  addE('right').from('d').to('e').
  addE('right').from('e').to('i').
  addE('left').from('i').to('j').
  addE('left').from('d').to('f').
  addE('right').from('b').to('h').
  addE('left').from('c').to('g').iterate()    

We can combine loops and index as follows (I added the unfold to improve readability):

gremlin> g.V().hasLabel('root').
......1>       emit().
......2>       repeat(group('x').by(loops()).by(values('data').fold().index()).out()).
......3>       cap('x').unfold()   

==>0=[[9, 0]]
==>1=[[5, 0], [11, 1]]
==>2=[[2, 0], [8, 1], [10, 2], [15, 3]]
==>3=[[1, 0], [22, 1]]
==>4=[[16, 0]]

Given your comment about a simpler form being acceptable I think the above gets pretty close. You should be able to tweak this query to make any changes in the output formatting that you require.

You can go one step further and group using the parent vertex as follows. From this you can build whatever projections of the final results you require.

gremlin> g.V().hasLabel('root').
......1>       repeat(outE().group('x').
......2>         by(loops()).
......3>         by(group().
......4>           by(outV()).
......5>           by(inV().values('data').fold().index())).
......6>         inV()).
......7>         times(4).
......8>       cap('x').
......9>       unfold() 

==>0={v[0]=[[5, 0], [11, 1]]}
==>1={v[2]=[[2, 0], [8, 1]], v[6]=[[10, 0], [15, 1]]}
==>2={v[4]=[[1, 0]], v[8]=[[22, 0]]}
==>3={v[16]=[[16, 0]]}       
Kelvin Lawrence
  • 14,674
  • 2
  • 16
  • 38
  • I want to determine which node of the previous level the current level nodes are attached. Check the later part of the question with depth and sub depth. If I can get this it can help. – Phoenix Jun 11 '20 at 12:33
  • In your last comment the example you gave had removed that need so I modeled this answer on that. Will your tree always bee a binary tree? – Kelvin Lawrence Jun 11 '20 at 12:37
  • No, the tree is not always binary, for simplicity I took that example for the binary tree you explained. The output must be as follows: depth: 0 sub-depth:0 data:9 depth: 1 sub-depth:1.1 data:5 depth: 1 sub-depth:1.2 data:11 depth: 2 sub-depth: 2.1 data:2 depth: 2 sub-depth:2.2 data:8 depth: 2 sub-depth:2.3 data:10 depth: 2 sub-depth:2.4 data:15 depth: 3 sub-depth:3.1 data:1 depth: 3 sub-depth:3.2 data:22 depth: 4 sub-depth:4.1 data:16 Also share you views on if we can get the output as I explained in the diagram initially. – Phoenix Jun 11 '20 at 12:44
  • Yes it can be done. I'll post an update a bit later now you have clarified what you need. – Kelvin Lawrence Jun 11 '20 at 12:55
  • For the question which I asked initially output for the binary tree must be as follows: depth:0 sub-depth:0 data:9 depth:1 sub-depth: 1.1 data:5 depth:1 sub-depth: 1.2 data:11 depth:2 sub-depth: 1.1.1 data:2 depth:2 sub-depth: 1.1.2 data:8 depth:2 sub-depth: 1.2.1 data:10 depth:2 sub-depth: 1.2.2 data:15 depth:3 sub-depth: 1.1.1.1 data:1 depth:3 sub-depth: 1.2.2.1 data:22 depth:4 sub-depth: 1.2.2.1.1 data:16 If we can get this that will be great. But previous comment will also work in other case. – Phoenix Jun 11 '20 at 13:09
  • I just edited the answer to show the basic building blocks of a query that group the results at each depth by their parent vertex. If this does not enable you to get across the finish line I can edit some more later. – Kelvin Lawrence Jun 11 '20 at 13:25
  • It's not working giving parent data for all the child nodes. – Phoenix Jun 11 '20 at 13:42
  • Let us [continue this discussion in chat](https://chat.stackoverflow.com/rooms/215818/discussion-between-vinayak-and-kelvin-lawrence). – Phoenix Jun 12 '20 at 12:58
  • Any solution for getting the required output shown in figure – Phoenix Jul 15 '20 at 14:49