2

I am using python to run my gremlin queries, for which I am still getting used to / learning. Let's say I have vertex labels A and B, and there can be an edge from A to B called abEdge. I can find B vertices that have such edges from a particular A vertex with:

g.V()\
    .hasLabel("A")\
    .has("uid", uid)\  # uid is from a variable
    .outE("abEdge")\
    .inV()\
    .toList()

But how would I go about finding B vertices that have no such edges from a particular A vertex?

My instinct is to try the following:

# Find B edges without an incoming edge from a particular A vertex
gremlin.V()\
    .hasLabel("B")\
    .where(__.not_(inE("abEdge").from_(
        V()\
        .hasLabel("A")\
        .has("uid", uid)
    )))\
    .next()

And that results in a bad query (Not sure where yet), I'm still reading up on Gremlin, but I am also under time contraints so here I am asking. If anyone can help but just using groovy syntax that is fine too as it's not too bad to convert between the two.

Any explanations would be helpful too as I am still learning this technology.

Update

I guess if this were a real-life question, and related to this website. We could ask (A=Person, B=Programming-Language, and abEdge=knows):

Which programming languages does particular person A not know?

alexexchanges
  • 3,252
  • 4
  • 17
  • 38

1 Answers1

2

It looks like you almost had the answer:

g.V().hasLabel("B"). \
  filter(__.not_(__.in_('abEdge').has("A","uid",uid))). \
  toList()

I prefer filter() when using just a single Traversal argument, but I think you could replace with where() if you liked.

stephen mallette
  • 45,298
  • 5
  • 67
  • 135
  • This was insightful, but I believe not what I am after. I would like a list of `B` vertices that have no edge called `abEdge` from a __particular__ `A` vertex given by a `uid` – alexexchanges Mar 17 '20 at 11:35
  • What are typical situations where distinguishing the use of `filter` or `where` is important? – alexexchanges Mar 17 '20 at 15:47
  • both take a single `Traversal` as an argument and do the same thing, so the question of use is a bit of a question of preference when you're calling it that way. For me, I tend to prefer `filter(Traversal)` over `where(Traversal)` and only save `where()` for its explicit cases where filter won't quite cut it, like when referencing a step label: `g.V(1).as('a').out('created').in('created').where(neq('a'))` – stephen mallette Mar 17 '20 at 15:54
  • I see. Thank you for your answer and insight. – alexexchanges Mar 17 '20 at 15:57
  • I would like to identify the has-node differently. So far I have used hasId('abc'). But I pass this very node earlier in the query and can store it with as('abc'). How would I use this information inside or instead of the has statement? – Meike Feb 24 '22 at 12:30