图计算介绍

概述

图(graph)是一种由顶点和边组成的数据结构。在计算机中建模的图,一般包含标记(label)和键值属性(key/value)。这种图的结构就叫属性图(property graph)。下图是一个称之为“TinkerPop Classic”的属性图示例。

TinkerPop Modern

TinkerPop3是TinkerPop图计算框架的第三个版本(incarnation)。类似于一般的计算过程,图计算可分为结构(structure,比如图graph)和处理(process,比如遍历traversal)两部分。图的结构指的是由顶点/边/属性等拓扑学概念所定义的数据模型。图的处理是分析图结构的手段或方法。

Graph Computing

TinkerPop3图处理API的主要组件

  • TraversalSource:针对特定图的遍历产生器(generator),DSL,执行引擎。
    1.Traversal<S, E>:一个功能性数据流处理过程,可将S类型的对象转换成E类型的对象
    2.GraphTraversal:面向原始图(raw graph)语义的遍历DSL

  • GraphComputer:一个在多机器集群上后台运行的、并行的、分布式的处理图的系统
    1.VertexProgram:通过消息交互,以逻辑上并行的方式,在所有顶点上执行的代码
    2.MapReduce:用于并行分析图中所有节点,并得到单一的归纳(reduced)结果的一组计算指令

图的结构(Graph Structure)

一个图的结构是在它的顶点,边,属性之中,显示地相互引用所形成的拓扑。一个顶点有其关联的边。一个顶点与另一个顶点共享一条边,那么它们就是相邻顶点。一个属性必定附属到一个元素上,而一个元素一般会有一个属性集合。一个属性是一个key/value对,其中key是一个字符串。TinkerPop3的图结构API提供了创建一个图结构所必要那些方法。

Graph graph = TinkerGraph.open(); (1)
Vertex marko = graph.addVertex(T.label, "person", T.id, 1, "name", "marko", "age", 29); (2)
Vertex vadas = graph.addVertex(T.label, "person", T.id, 2, "name", "vadas", "age", 27);
Vertex lop = graph.addVertex(T.label, "software", T.id, 3, "name", "lop", "lang", "java");
Vertex josh = graph.addVertex(T.label, "person", T.id, 4, "name", "josh", "age", 32);
Vertex ripple = graph.addVertex(T.label, "software", T.id, 5, "name", "ripple", "lang", "java");
Vertex peter = graph.addVertex(T.label, "person", T.id, 6, "name", "peter", "age", 35);
marko.addEdge("knows", vadas, T.id, 7, "weight", 0.5f); (3)
marko.addEdge("knows", josh, T.id, 8, "weight", 1.0f);
marko.addEdge("created", lop, T.id, 9, "weight", 0.4f);
josh.addEdge("created", ripple, T.id, 10, "weight", 1.0f);
josh.addEdge("created", lop, T.id, 11, "weight", 0.4f);
peter.addEdge("created", lop, T.id, 12, "weight", 0.2f);

图的变形(Mutating the Graph)

Graph graph = TinkerGraph.open();
// add a software vertex with a name property
Vertex gremlin = graph.addVertex(T.label, "software",
                             "name", "gremlin"); (1)
// only one vertex should exist
assert(IteratorUtils.count(graph.vertices()) == 1)
// no edges should exist as none have been created
assert(IteratorUtils.count(graph.edges()) == 0)
// add a new property
gremlin.property("created",2009) (2)
// add a new software vertex to the graph
Vertex blueprints = graph.addVertex(T.label, "software",
                                "name", "blueprints"); (3)
// connect gremlin to blueprints via a dependsOn-edge
gremlin.addEdge("dependsOn",blueprints); (4)
// now there are two vertices and one edge
assert(IteratorUtils.count(graph.vertices()) == 2)
assert(IteratorUtils.count(graph.edges()) == 1)
// add a property to blueprints
blueprints.property("created",2010) (5)
// remove that property
blueprints.property("created").remove() (6)
// connect gremlin to blueprints via encapsulates
gremlin.addEdge("encapsulates",blueprints) (7)
assert(IteratorUtils.count(graph.vertices()) == 2)
assert(IteratorUtils.count(graph.edges()) == 2)
// removing a vertex removes all its incident edges as well
blueprints.remove() (8)
gremlin.remove() (9)
// the graph is now empty
assert(IteratorUtils.count(graph.vertices()) == 0)
assert(IteratorUtils.count(graph.edges()) == 0)
// tada!

图的处理(Graph Process)

处理图的主要方法是图的遍历。一次遍历指的是,根据图数据结构中的指涉结构(referential structure),按一定算法步骤来走遍图中指定的元素。举例说明

What software does vertex 1’s friends work on?
1.Start at vertex 1.
2.Walk the incident knows-edges to the respective adjacent friend vertices of 1.
3.Move from those friend-vertices to software-vertices via created-edges.
4.Finally, select the name-property value of the current software-vertices.

GraphTraversalSource继承自TraversalSource,提供的了两种遍历的方法。

  1. GraphTraversalSource.V(Object... ids)
  2. GraphTraversalSource.E(Object... ids)

v()E()的返回类型为GraphTraversalGraphTraversal支持函数式编程(function composition)。GraphTraversal的每一个方法称为一步(step),每一步会以五种常用方式中的一种来转调(modulate)上一步的结果。

  1. map:将一个对象转换成另一个对象(S -> E)
  2. flatMap:将一个对象转换成另一些对象的迭代器(S -> E*)
  3. filter:允许或不允许遍历器进行下一步的处理(S → S ∪ ∅).
  4. sideEffect:不改变当对象,但会产生计算副作用(S ↬ S)
  5. branch:将对象送到任务的分支中(S → { S1 → E, …, Sn → E } → E*)

示例

$ bin/gremlin.sh

         \,,,/
         (o o)
-----oOOo-(3)-oOOo-----
gremlin> graph = TinkerFactory.createModern() (1)
==>tinkergraph[vertices:6 edges:6]
gremlin> g = graph.traversal(standard())        (2)
==>graphtraversalsource[tinkergraph[vertices:6 edges:6], standard]
gremlin> g.V().has('name','marko').out('knows').values('name') (3)
==>vadas
==>josh
gremlin> marko = g.V().has('name','marko').next() //(1)
==>v[1]
gremlin> g.V(marko).out('knows') //(2)
==>v[2]
==>v[4]
gremlin> g.V(marko).out('knows').values('name') //(3)
==>vadas
==>josh

遍历器(Traverser)

示例path()

gremlin> g.V(marko).out('knows').values('name').path()
==>[v[1], v[2], vadas]
==>[v[1], v[4], josh]

示例repeat()

gremlin> g.V(marko).repeat(out()).times(2).values('name')
==>ripple
==>lop

关于Gremlin语言变体

  • Gremlin-Groovy
  • Gremlin-Scala
  • Gremlin-JavaScript
  • Gremlin-Clojure

供应商集成

TinkerPop是一个由各种互相协作组件组成的框架。核心API(core API)定义了什么是图,顶点,边等。供应商必须实现核心API。一旦实现,那么用户就能使用Gremlin遍历语言了。然而,供应商还可以更进一步提供特殊化的TraversalStrategy优化策略,以便供应商在运行时检查Gremlin查询,同时优化它们的执行(比如使用索引查询,步骤顺序优化)。如果供应商的图系统是图处理器(graph processor,提供OLAP能力),那么供应商可实现GraphComputerAPI。这些API定义了如何在工作者(worker,比如线程或机器)进行消息或遍历器的通讯。
Gremlin语言将图以顶点和边进行转义,它是一种基于图的领域专属语言。用户可以定义属于自己的高阶领域专属语言去进行图处理。Gremlin服务器可用于与TinkerPop使能的图系统进行可靠通讯。

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 159,835评论 4 364
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,598评论 1 295
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 109,569评论 0 244
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 44,159评论 0 213
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,533评论 3 287
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,710评论 1 222
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,923评论 2 313
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,674评论 0 203
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,421评论 1 246
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,622评论 2 245
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,115评论 1 260
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,428评论 2 254
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,114评论 3 238
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,097评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,875评论 0 197
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,753评论 2 276
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,649评论 2 271

推荐阅读更多精彩内容