首页 > 解决方案 > Gremlin - 查找和连接子图

问题描述

我的图表包含一个无向拓扑网络数据,我的目标是构建一个查询,查找适用于特定网络规则的所有子网络,为每个子网络创建顶点并连接它们之间有路径的那些。目的是通过替换一个顶点中的每个子网子图来最小化大图。为了找到所有子网,我从 gremlin recopies 中获取了“连接的组件”查询,并将我的网络规则添加到停止条件中。但是现在我很难将这个子网络相互连接起来。

我在这里提供了包含 PC、路由器和其他设备节点的示例图形脚本(使用不同的网络域)。查询应该通过对连接的 PC 进行分组来查找所有 LAN,并为每个 LAN 返回具有其路径的其他 LAN id。

方向在该图中没有意义,子图之间的路径可能包含多种类型的节点(路由器、设备等)。
我的 GraphDB 是 OrientDB。

网络图图像

结果应如下所示:

==>LAN 1: {pcs: [1, 2, 3], connected LANs: [LAN 2, LAN 3]}  
==>LAN 2: {pcs: [4, 5, 6], connected LANs: [LAN 1]}  
==>LAN 3: {pcs: [8, 7], connected LANs: [LAN 1]}  

这是查询的第一部分(查找所有子网络):

g.V().hasLabel('PC').emit(cyclicPath().or().not(both())).
 repeat(__.where(without('a')).store('a').both()).until(or(cyclicPath(), hasLabel('Router'))).
 group().by(path().unfold().limit(1)).
 by(path().local(unfold().filter(hasLabel('PC')).values('id')).unfold().dedup().fold()).unfold()

我的问题是:

  1. 我可以通过从每个子网络遍历某个任意节点直到到达其他子网络上存在的节点来识别子网络之间的连接。我如何在 gremlin 中编写它
  2. 如何从此查询结果中创建新图表?
  3. 这种类型的查询在大图中的性能如何,比如 30M 个节点?

创建图形脚本:

g = TinkerGraph.open().traversal()
g.addV("PC").property("id","1").as("pc1").
addV("PC").property("id","2").as("pc2").
addV("PC").property("id","3").as("pc3").
addV("PC").property("id","4").as("pc4").
addV("PC").property("id","5").as("pc5").
addV("PC").property("id","6").as("pc6").
addV("PC").property("id","7").as("pc7").
addV("PC").property("id","8").as("pc8").
addV("Router").property("id","9").as("router1").
addV("Router").property("id","10").as("router2").
addV("Equipment").property("id","11").as("eq1").
addV("Equipment").property("id","12").as("eq2").
addV("Equipment").property("id","13").as("eq3").
addV("Equipment").property("id","14").as("eq4").
addE("Line").from("pc1").to("pc2").
addE("Line").from("pc1").to("eq3").
addE("Line").from("pc2").to("pc3").
addE("Line").from("pc3").to("eq1").
addE("Line").from("pc3").to("eq3").
addE("Line").from("pc4").to("pc5").
addE("Line").from("pc4").to("pc6").
addE("Line").from("pc5").to("pc6").
addE("Line").from("pc7").to("pc8")
addE("Line").from("router1").to("pc7").
addE("Line").from("router1").to("pc8").
addE("Line").from("router1").to("eq2").
addE("Line").from("router2").to("eq4").
addE("Line").from("eq1").to("router1").
addE("Line").from("eq3").to("router2").
addE("Line").from("eq4").to("pc4").
iterate()

标签: orientdbgremlingraph-databases

解决方案


这不是一个很好的答案,因为我认为我必须跳到您的最后一个问题并忽略三个问题中的前两个:

这种类型的查询在大图中的性能如何,比如 30M 个节点?

如果您修改了此处找到的“连接组件”配方,那么我假设您进一步阅读了有关 OLTP 和 OLAP 的此类查询的一般费用。我想对于 30M 顶点,您应该查看基于 OLAP 的处理(与您上面介绍的脚本相反)。我想您可能可以在具有大量内存的足够大的机器上使用 TinkerGraph/GraphComputer 完成此操作,但这可能只是本食谱末尾SparkGraphComputer所建议的工作。

我认为你的前两个问题似乎取决于你解决第三个问题的方法和成功,一旦你走到那一步,这些最初的问题可能会变得更加集中,甚至会发生一些变化。也许最好尝试解决您的“连接组件”的 OLAP 方法,然后再提出一些更具体的问题。


推荐阅读