Gremlin 小精灵-如何简化2计数数组上的{a-b}数学?
我正在尝试做一些应该很简单的事情。我有一个包含两条边的数组流。对于每个数组,我只想从第一条边减去第二条边上的值。在某些语言中,这可能只是Gremlin 小精灵-如何简化2计数数组上的{a-b}数学?,gremlin,tinkerpop,Gremlin,Tinkerpop,我正在尝试做一些应该很简单的事情。我有一个包含两条边的数组流。对于每个数组,我只想从第一条边减去第二条边上的值。在某些语言中,这可能只是array[0]。value-array[1]。value。然而,我仅通过以下方式实现了这一目标: local( project('a', 'b'). by(unfold().limit(1)). by(unfold().tail(1)). math('a - b'). by('bias')) 这是可行的,但
array[0]。value-array[1]。value
。然而,我仅通过以下方式实现了这一目标:
local(
project('a', 'b').
by(unfold().limit(1)).
by(unfold().tail(1)).
math('a - b').
by('bias'))
这是可行的,但是如果没有project()
、limit()
和tail()
,这应该会简单得多。这也让我质疑,如果数组中有3个或更多项,如何从数组中获取正确的项。如果第二项不再是tail()
,我将如何获得它?我猜极限(2)。尾部(1)
?看起来非常混乱。如果我简单地使用fold()
步骤,我可以非常接近于简化此操作:
local(
unfold().
values('bias').
fold(0, minus))
以这种方式使用fold()
非常干净,但是会导致0-a-b
。如果我可以用一个动态的值来替换这个种子,那么我可以获得更多。但即使这样,我也必须做一些类似于(2*a)-a-b
,以获得正确的结果。尝试将0
种子替换为动态变量,如limit(1)。值('bias')
由于类型错误而失败。但无论如何,我都不会满足于这样的任意代码。然后,我最后的想法是为项目编制索引,然后按索引进行选择:
local(
index().
with(WithOptions.indexer, WithOptions.map))
虽然边的索引很好,但我找不到一种方法使其有用。我想我可以选择('0')
来获取第一项,但是没有返回任何内容
我想我的问题如下:
是否有一种简单的方法可以实现a-b
,就像a+b
是通过sum()或fold(0,sum)
实现的一样?
如果没有,是否有更干净的方法来选择数学数组中的项目?还是应该在数学之前把所有的东西都放进project()
?这看起来太麻烦了…你可以很容易地跳过project()
:
gremlin> arr = [[g.E(7).next(),g.E(8).next()],[g.E(8).next(),g.E(10).next()]]
==>[e[7][1-knows->2],e[8][1-knows->4]]
==>[e[8][1-knows->4],e[10][4-created->5]]
gremlin> g.inject(arr).unfold().as('a','b').
......1> math('a - b').
......2> by(limit(local,1).values('weight')).
......3> by(tail(local,1).values('weight'))
==>-0.5
==>0.0
您仍然必须unfold().limit()/tail()
,但我认为这是一种更好的方法,因为它可以避免创建一个映射图而将其扔掉
这也让我质疑,如果数组中有3个或更多项,如何从数组中获取正确的项。如果第二项不再是尾部,我怎么才能得到它呢?我猜是极限(2)。尾巴(1)
您可以使用range()
来避免多步骤方法:
gremlin> arr = [[g.E(7).next(),g.E(8).next(),g.E(9).next()],[g.E(8).next(),g.E(10).next(),g.E(10).next()]]
==>[e[7][1-knows->2],e[8][1-knows->4],e[9][1-created->3]]
==>[e[8][1-knows->4],e[10][4-created->5],e[10][4-created->5]]
gremlin> g.inject(arr).unfold().as('a','b').
......1> math('a - b').
......2> by(limit(local,1).values('weight')).
......3> by(range(local,1,2).values('weight'))
==>-0.5
==>0.0
您可以使用sack()
来避免math()
,但我不确定它是否简化了内部列表的分类(即您仍然坚持限制()
/尾部()
):
顺便提一下,这是个好问题。方法很棒。到目前为止,我甚至从未想过使用带有两个字符串的as()
。当我们讨论这个主题时,有没有办法在index()
之后分离数组?与使用映射选项进行索引和选择例如索引2一样,任何列表/数组都可以使用unfold()
展平为流,或者使用range()
定向步骤使用local
范围进行拆分。如果这还不清楚,或者如果我误解了,也许可以提出一个新问题,我可以试着更完整地回答。当我做出这样的回答时,我正在考虑挑选一张地图。但现在我想得更清楚了,不仅不需要地图,而且还可以使用select(values)
将地图展平为其值。你说得对。再次感谢。
gremlin> arr = [[g.E(7).next(),g.E(8).next()],[g.E(8).next(),g.E(10).next()]]
==>[e[7][1-knows->2],e[8][1-knows->4]]
==>[e[8][1-knows->4],e[10][4-created->5]]
gremlin> g.withSack(0).inject(arr).unfold().
......1> sack(assign).by(limit(local,1).values('weight')).
......2> sack(minus).by(tail(local,1).values('weight')).
......3> sack()
==>-0.5
==>0.0