图数据库简介(译)

提要

  1. 图及其相关术语介绍
  2. 图数据库如何解决复杂数据关系问题
  3. 图数据库相对于关系数据库的优势
  4. 选型问题,什么情况下使用图数据库

       现代应用程序是建立在数据之上的,而且数据的规模和复杂性都在不断增加。纵使数据越来越复杂,我们也无限期盼应用程序能从中分析出有价值的东西。如果您年长一点,您可能还记得应用程序加载数据和分析数据需要很长时间,而且功能有限。今天不同了,应用程序提供了强大、灵活和即时的数据分析能力。但是,对于现代应用程序解决的每100个问题,最常用的数据工具(关系数据库)只能很好地解决其中88个问题。余下的12个问题,关系数据库无能为力。这些剩余的问题涉及数据中的链接和连接,这些方面的数据可以产生强大和独特的见解。这将我们推到了一个决策的十字路口:我们可以使用关系数据库“斧劈锤凿”式地来处理这些问题,并使其足够好地工作,或者可以换一个角度思考,看看哪些其他工具可以更好、更快、更省力地解决这些问题。

通过这本书,可以让你原有关系数据库基础上换一种角度思考,并研究一条僻径:图数据库。本书是为开发人员、开发工程师和架构师编写的,这对他们解决高度复杂链接和连接的数据工作会非常有益处。在学习本书之前,我们假设您已经熟悉关系数据库,但对何时、何地和如何学习图数据库是一个更好的工具感兴趣。

本书的目标是让您掌握并把图数据库作为您工作中的常用工具。我们多么希望当初在开始构建以图为基础的应用程序时能有这样一本书作为指导。本书将以常见的图模式贯穿始终,这些图模式将展示出关系数据库不容易实现的数据分析能力。

我们的主要方法是通过构建虚拟餐厅评论和推荐应用程序(称为“ DiningByFriends”)的示例。当我们从规划、分析、设计到实现整个软件开发生命周期过程中,应用程序演示了如何思考和处理图数据。 本书的每一章都建立在上一章的基础上,我们将利用图形数据库创建一个功能良好的应用程序。 我们认为,通过解决一组现实问题,使这些概念发挥作用,即使它们有点简单,也是使用和学习新技术最佳途径。让我们从介绍什么是图和图数据库,以及它们与传统数据库(如关系数据库)的比较,开始我们的图数据库之旅吧。

    1. 什么是图?

当您查看路线图、检查组织结构图或使用社交网络,如:Facebook、LinkedIn或Twitter,您就在使用图。图几乎无处不在,从现实场景中抽象出实体和实体关系,并快速有效的处理这些数据的内部复杂逻辑,这也是您思考现实场景中的方法。

让我们用“逛超市”这个常见的例子来说明。在一张纸上画出从你家到超市的路线图,它很可能看起来如图1.1所示。

图1.1显示了一个图表,图中抽象了关键节点和节点间关系。首先,我们提取关键位置(如交叉点),我们用圆表示。然后,我们将这些关键交叉点之间的连接指定为线,以显示关键交叉点之间的关系。这只是我们如何自然地将现实问题表示为图的一个示例。

 

图1.1  表示通往超市的有向图

抽象现实世界的实体及其关系是人类的天性,这种抽象结构的数学名称是图。 当我们考虑一组包含大量高度互连的数据时,我们也可以将这个数据集描述为一个相互关联的事物网络,这只是表示图的另一种方式。

在地图上,城市经常用圆圈来表示,连接它们的道路用线条来表示。 在组织结构图(orgchart)上,圆圈通常代表一个人,通常有一个相关的标题,将这些人连接在一起的线条显示雇主-雇员关系。 在社交网络中,人们通过朋友或关注而彼此联系。 这种实体及其之间的关系是图论和图论的基本基础。图论已经被数学家定义和研究了几个世纪,我们也将图论中使用的这些定义作为我们的起始术语:

  1. 图(Graph)—顶点(奇异点、顶点)和边的集合
  2. 顶点(Vertex)—图中零条或多条边相交的点,也称为节点或实体
  3. 边(Edge)—图中两个顶点之间的连线,称为关系、链接或连接

欧拉与图论的起源

图论的起源通常认为归因于1736年莱昂哈德.欧拉LeonhardEuler(发音为“OI-ler”)发表的一篇关于哥尼斯堡(Konigsberg)七桥问题的论文。

哥尼斯堡(现在俄罗斯加里宁格勒)是一座位于布格(Pregel)河上的普鲁士城市。 这条河包含两个岛屿,由七座桥把两个岛屿与河岸连接起来。 问题是:设计一条路线,让镇上的市民能够一次穿过所有七座桥,而且每座桥只准经过一次。 欧拉(Euler)把这个问题抽象为图的问题,他把每一块陆地用一个顶点表示,将一座桥用连接两个顶点的边来表示。基于这种抽象,欧拉指出,这个问题没有解,在这个问题中拓扑结构起到了非常重要的作用。欧拉也成为了图论和拓扑学的创始人。

虽然定义很好,但是图形直观。

在使用图时,图通常由表示顶点的圆和表示边的线组成,如图1.2所示。

 

图1.2 用表示顶点的圆和表示边的线来表示图

注:在本书中,我们使用了顶点和边这两个术语。一些图数据库使用术语节点代替顶点,使用关系代替边,但这些在概念上是相同的,只是说法不同而已。

对于软件开发人员来说,图并不是新概念。图是我们一直在软件开发中使用的许多常见数据结构的基础,甚至可能还没有意识到。只是我们没有意识到这一点。常见的数据结构(如链表和树)只是具有特定规则的图的类型。尽管这些数据结构对于开发人员是众所周知的,但通常会抽象出特定于图形的实际实现细节。

      1. 什么是图数据库?

图数据库是一种数据存储引擎,它将顶点和边的基本图结构与持久化技术和遍历(查询)语言结合起来,以创建一个用于存储和快速检索高度关联的数据而优化的数据库。实体之间的关系与数据中的实体同等或更重要。因为在图数据库中实体和关系被同等重视,所以我们可以更准确,更轻松地表示和推理真实世界的关系,尤其是与其他数据库技术相比时。正如我们将在本书中展示的那样,图形数据库是更好的工具,既可以表示事物之间丰富多样的关系,又可以根据这些关系识别模式。

让我们简单地看看图数据库与关系数据库在处理多种不同类型数据关系的一些挑战。 关系数据库(有点讽刺意味)在表示丰富的关系方面相当差。 关系数据库中的关系是外键,是指向其他表中主键的指针。这些指针的变化不是我们可以轻易观察和操控的东西。相反,外键在查询时从一行跟随到另一行。(尽管有可能,但反向执行这些操作通常代价高昂。)查找表或链接表不再使用仅查询时间指针(query-time-only-pointer)的结构,以允许存储有关关系的属性,类似于图形数据库中的边结构。

另一方面,图形数据库为我们的数据中的关系移动提供了极好的工具。通过使连接(边)与项(边)一样重要,边连接到(顶点),图形数据库将这些关联表示为数据库的完整结构,易于观察和操作。这种存储丰富关系的能力也是图形数据库更适合处理复杂的链接数据用例的主要原因之一。用开发者的话说,我们可以说边和顶点一样是“一等公民”。也就是说,关系在数据模型中与事物或实体一样重要和有用。

最后一点是,图形数据库可以提高开发人员解决某些问题的效率,这是其他技术无法做到的。以更好地代表真实世界中对应数据的方式存储数据,可以让开发人员更容易地推理和理解他们所在的领域。使得新团队成员在学习其领域及其数据库表示时能够更快地熟悉。

      1. 图数据库与其他类型数据库的比较

虽然这本书的重点是图数据库,它把关系数据库作为主要的对比对象,但我们应该注意的是,数据库领域不限于这两种类型的数据存储。 从广义上讲,数据库可以分为以下五种方式之一的引擎类型。 图1.3总结了这些类型引擎之间的关系:

  1. 键值类型数据库Key-value)-通过唯一标识符(键Key)和相关数据对象(值Value)表示所有数据。 例如:Berkeley DB、Rocks DB、Redis和Memcached。
  2. 列存储数据库(Wide-column )(或面向列)-将数据存储在行中,每行中的列数可能会很大,或者可能会有所不同。 例如Apache HBase、Azure Table Storage、Apache Cassandra和Google Cloud Bigtable。
  3. 文档型数据库(Document)-把数据存储在一个唯一的键控文档中,该文档可以具有不同的结构,并且可以包含嵌套数据。 例如Mongo DB和Apache Couch DB。
  4. 关系型数据库Relational)-在包含具有严格模式的行表中存储数据。 可以在允许行连接的表之间建立关系。 例如Postgre SQL、Oracle数据库和Micros of tSQLServer。
  5. 数据库Graph)-将数据存储为顶点(节点、实体)和边(关系)。 例如Neo4j、Apache Tinker Pop的Gremlin Server、Janus Graph和Tiger Graph。

 

图1.3 按数据复杂度排序的数据库引擎类型

从这些示例中可以看到,默认情况下,只有关系数据库和图形数据库具有处理数据中关联实体的功能。 在键值、宽列或文档数据库的特定实现中也可能会这样做,但这通常是由供应商为特定的需求而开发的。 因为我们的重点是图数据库,只有与关系数据库才有可比性,所以我们的其余讨论仅限于这两种类型的数据库引擎。

      1. 为什么我不能使用SQL?

作为开发人员,我们经常选择熟悉的工具而不是最优的工具,尤其是在处理数据库时。大多数开发团队对关系数据库的细节都有深入的了解,但很少有团队具备其他类型数据库的专业知识。因此,我们经常为了方便就选择或默认的使用关系数据库,而忽略有更好的工具来解决某些问题。

我们并不是说关系数据库是一个糟糕的工具。事实上,这通常是我们在处理自己的应用程序时要达到的第一个目标。 但是关系数据库有其局限性。 虽然可以使用具有高度连接数据的关系数据库,但在许多情况下,可以通过使用为这些类型的用例设计的工具来简化工作。 在本节中,我们将讨论图数据库在三个方面所提供的比使用关系数据库更简单、更优雅的解决方案:

  1. 递归查询(例如,组织的员工报告层次结构或组织结构图)
  2. 不同的类型结果(例如,订单和产品报告示例)
  3. 路径(例如,一个过河智力题)

对于本章,我们选择了三个不同的示例来表示这三个唯一的图数据库功能。 从下一章开始,我们将介绍“DiningByFriends”问题,并开始正式的数据建模过程。 在这一点上,大多数示例将跟随这个示例的开发而展开。 但在此之前,我们将使用各种方法向您介绍图和图数据库的基本概念。

递归查询(RECURSIVE QUERIES

递归查询就是连续执行多次,反复调用自己,直到达到某种转义或终止条件。 关系数据库不能很好地处理递归操作(特别是无界操作),它既不能处理语法,也不能处理性能。 因为这样会导致编写和维护复杂的查询,对数据进行过度的去规范化,或者同时执行两项操作,以便即时返回结果。

另一方面,图数据库使用它们丰富的关系表示来干净有效地处理这些无界递归查询。 为了了解我们正在讨论的内容,让我们看看在SQL和图数据库中递归查询是什么样子。 给定一个公司的员工和经理列表,如图1.4所示,让我们检查如何确定一个人的报告层次结构。

为了在关系数据库中建模此层次结构,下面的查询显示了如何定义表。 然后,我们采取这个表模式,并列出数据(表1.1):

/*建表代码*/

CREATE TABLE org_chart (

 employee_id SMALLINT NOT NULL,

 manager_employee_id SMALLINT NULL,

 employee_name VARCHAR(20) NOT NULL

);

 

图1.4 公司中组织层次结构,演示递归查询

表1.1 关系数据库中公司管理层次结构的示例数据

 

然后,我们使用递归函数查询这些数据以找到用户的管理层次结构。 下面的代码片段显示了查询:

WITH RECURSIVE org AS (

 SELECT employee_id,

 manager_employee_id,

 employee_name,

 1 AS level

 FROM org_chart

 UNION

 SELECT e.employee_id,

 e.manager_employee_id,

 e.employee_name,

 m.level + 1 AS level

 FROM org_chart AS e

 INNER JOIN org AS m ON e.manager_employee_id = m.employee_id

 )

SELECT employee_id, manager_employee_id, employee_name

FROM org

ORDER BY level ASC;

如果您曾经在SQL中编写过像我们的管理层次结构查询那样的共用表表达式CTEs(Common Table Expressions),那么您就知道这些表达式的编写和调试可能很复杂,并且由于性能差而臭名昭著。 另一方面,像前面的层次结构示例一样,嵌套查询和递归查询是对图形数据库进行优化以回答的问题类型。 例如,图1.5显示了相同数据作为图的样子。 为了在图中找到用户的管理链,我们需要编写一个类似于SQL查询的查询,在图中,SQL查询被称为遍历。 对于我们的层次结构示例,我们将得到如下的遍历:

g.V().

 repeat(

 out('works_for')

 ).path().next()

 

图1.5 以圆为顶点,箭头为边的组织层次结构的图表示

注意,遍历查询我们使用的是一个名为Gremlin的图形查询语言,我们将在本书中使用它。 现在,没有必要精确地理解它是如何工作的。 我们将从第三章开始深入研究细节。 现在,请注意与以前的SQL查询相比,此查询相对简单。

此示例演示了简单易懂的特性,您可以使用该特性对图进行查询递归查询。如果我们将其与图1.5进行比较,我们可以看到这种遍历何其自然地映射到我们的本能,以直观地导航数据的层次结构。

不同的结果类型(DIFFERENT RESULT TYPES)

您是否有过从不同数据类型的单表构成的数据库返回不同类型的结果集? 虽然通过将所有表格中的所有列结合起来实现这一点是可能的,但它的结果往往低于理想结果。 图数据库的优点之一是能够在结果中返回不同的数据类型。 让我们看看关系数据库和图形数据库在返回不同类型时是如何比较的。

例如,假设我们有一个订单处理系统,我们不仅要返回订单信息,而且还要返回产品信息。 图1.6表示关系数据库中带有表的传统实现。

 

图1.6 关系数据库中的订单和产品表;注意列名的差异

下面的代码片段展示了如何编写查询来检索带有关联产品信息的订单。 表1.2显示了此查询的结果集。

SELECT id,

 name,

 address,

 null AS product_name,

 null AS cost,

 'Order' AS object_type

FROM Orders

UNION

SELECT id,

 null AS name,

 null AS address,

 product_name,

 cost,

 'Product' AS object_type

FROM Products;

表1.2 从检索订单和相关产品信息的SELECT查询中得到结果集

 

从结果中,我们看到这两种不同的数据类型的结合形成的结果表明,我们的答案包含大量的空值(null)(通常称为稀疏数据或稀疏矩阵)。 这大量的空数据是因关系数据库指定的结果集必须包含一组列,而这两个表之间的列不一致引起的。 在数据稀疏的情况下,这不仅是增加返回的数据量,也减少了对数据结构的描述。 让我们来看看同样的数据是如何出现在图形数据库中的(图1.7)。

 

图1.7 订单产品信息示例显示为图中的顶点(边不建模)

使用这个图,我们可以编写一个图遍历来返回产品和订单数据。 在本例中,图数据库返回这些结果:

gremlin> g.V().valueMap(true)

==>[label:order, address:[123 Main St], name:[John Smith], id:1]

==>[label:order, address:[234 Park St], name:[Jane Right], id:2]

==>[label:product, cost:[10.76], id:234, product_name:[widget 2]]

==>[label:product, cost:[5.95], id:123, product_name:[widget 1]]

与之前的SQL结果相比,从图数据库返回的数据保留了对象是什么和它表示什么的语义,而没有无关的空(null)数据。 由于图形数据库提供了返回不同数据的灵活性,所以在处理复杂度不同的数据类型时,我们可以创建更干净的代码。

路径(PATHS)

路径是顶点和边的序列,描述了遍历如何在图中移动。例如,在Google或AppleMaps中,两个位置之间的一组方向。 返回数据库中两个对象如何在相互连接的能力是图形数据库特有的特性。

让我们看看一个经典的智力题,被称为“过河问题”,以说明如何利用路径这种新颍的方式解决问题的。 问题是这样,一位农民(farmer)带了一只狐狸(fox)、一只鹅(goose)和一袋大麦(barley),必须通过一条船过河。 然而,过河受到以下限制:

  1. 在每次过河,除了农民外,船只能携带一件物品。
  2. 每次过河农民都必须在。
  3. 狐狸不能单独和鹅在一起,否则它会吃掉它。
  4. 鹅不能单独和大麦一起,否则它会吃麦。

使用关系数据库,如果不使用暴力方法计算所有可能的组合,我们就找不到解决这个问题的方法。 然而,有了一些聪明的数据建模和路径查找算法的功能,用一个图来回答这个问题是相当简单的。 首先,将系统的初始状态建模为图中的顶点。 我们将其称为顶点TGFB_,其中每个字符表示问题的一部分:

T (农民和船)

G (鹅)

F (狐狸)

B (大麦)

_ (河)

这个TGFB_顶点通过告诉我们船(T)、鹅(G)、狐狸(F)和大麦(B)都在河(_)的一侧来编码问题的状态)。 我们的目标是要所有这些都在河的另一边的状态。

对于表示可能状态的顶点,我们使用边来显示如何从一个状态过渡到下一个状态。 例如,图1.8显示了农民把鹅带到河的另一边的状态变化,使狐狸和大麦停留在最初的一侧。图1.9显示了将所有潜在选项建模为这些状态(顶点)和状态变化(边)的表示的结果。

 

图1.8 图表示农民用船(T)带鹅(G)过河(_),留下狐狸(F)和大麦(B)

 

图1.9 利用寻路算法绘制过河问题的图形 请注意,任何违反突出显示的约束的状态都清楚地描述了可能的解决方案

图1.10说明了如果我们通过删除违反约束和相邻关系(边)的任何状态(顶点)来简化图会发生什么。 我们可以通过删除连接回先前状态的任何边来进一步简化我们的图,因为这将导致我们到达以前的状态(称为图中的循环)。

 

图1.10 使用图寻路算法,保保留了有效的状态

通过分析图1.10,我们看到了两个独立的路径来达到我们想要的状态。 为了查询图形返回这些路径,我们只需利用图形数据库的路径查找功能来返回这两条适当的路径,如此遍历所示:

g.V('TFGB_').

 repeat(

 out()

 ).until(hasId('_TGFB')).

 path().next()

当我们运行这个遍历时,它不仅返回访问的第一个和最后一个顶点,而且还返回沿途访问的整个顶点和边集。 这两个列表表示解决方案的两个不同路径:

TFGB_ -take goose-> FB_TG -take empty-> TFB_G -take barley-> F_TGB -return

goose-> TFG_B -take fox-> G_TBF -return empty-> TG_FB -take goose-> _TGFB

TFGB_ -take goose-> FB_TG -take empty-> TFB_G -take fox-> B_TFG -return

goose-> TGB_F -take barley-> G_TBF -return empty-> TG_FB -take fox-> _TGFB

虽然这个例子仅是一个智力题,但它代表了在许多现实世界的应用中发现的相同的基本问题,例如在地图上规划一条路线,在物流系统中找到最佳的配送方案,或者在社交网络中找到人与人之间的关系。 这些情况中的每一种基本上都是关于确定从一个实体到另一个实体的最佳步骤集。 图数据结构可以利用这样的路径查找功能,这在其他数据库类型中是难以实现的。

    1. 我的问题是图问题吗?

从社交网络分析、推荐引擎、依赖分析、欺诈检测和主数据管理(master data management),到在互联网上搜索问题和研究,您将很快遇到一个良好的图数据库用例清单。许多这样的列表的难点在于,除非您的问题是所指定的问题之一,否则很难知道它如何或是否非常适合图数据库。

 在本节中,我们将以更通用的方式来研究问题,而不是关注特定的用例。 这在某种程度上是概念性的,但我们发现很难从一个例子推广到一个特定的问题域。 我们将首先定义一个一般问题,然后提供一些例子来说明。 然后,我们将用一个评估问题的一般框架和一个决策树(这是一种图形形式!)作为决定是否使用图数据库的工具来结束本节。

1.2.2 问题探索

在阅读互联网上可用的图数据库上的大量信息时,你可能会看到这样一种说法:“...一切都是图”的确,现实世界很容易用图表来描述,但说一切都可以由一种类型的数据库解决的,这是一种武断的说法。 仅仅因为问题可以表示为图,并不一定意味着图数据库是解决该问题的最佳技术。

我们的过程从一个简单的问题开始:“我们试图解决什么问题?”回答此问题可提供有关我们将要问哪些问题的关键细节,并且这将决定我们需要存储的数据类型以及如何检索它们。我们将答案分为以下几类问题:

  1. 选择/搜索
  2. 相关或递归
  3. 聚合
  4. 模式匹配
  5. 中心性,聚类性和影响力

让我们依次检查发上其中的每一项,并讨论什么情况下使用图数据库。

选择/搜索(SELECTION/SEARCH

我们将以下类型的问题归类为搜索或选择问题。 这些问题狭隘地集中在一小部分实体,这些实体具有相同的属性,如名称、位置或雇主:

  • 给我所有在X工作的人?
  • 在我的系统里像约翰这样的名字的人?
  • 在X英里内的所有商店?

这些问题不需要数据内的丰富关系。在大多数数据库中,要回答这些问题,都需要使用单个过滤条件或可能使用索引。尽管您可以使用图形数据库来回答这些问题,但是这些问题不会使用或不需要图形特定的功能。相反,建议您使用关系数据库,如Postgre SQL(https://www.postgresql.org)或搜索技术,如Apache Solr(http://lucene.apache.org/solr)或Elasticsearch(https:/www.elastic.co)。这些数据库或工具要么更成熟(例如RDBMS),要么更优化(例如搜索工具)来解决这些问题。 由于这些问题并未利用我们数据中的关系,根据我们的经验,这些问题承担图形数据库的额外复杂性是不值得的。

结论:对于这些类型的问题,使用RDBMS或搜索技术。

相关或递归(RELATED OR RECURSIVE DATA)

探索实体之间关系的问题可增加含义并为数据提供拓扑价值,从而为图形数据库提供了强大的用例。这类问题的一些示例包括:

  1. 把我介绍给X公司的高管最简单的方法是什么?
  2. 约翰和宝拉是怎么认识的?
  3. X公司和Y公司有什么关系?

图形数据库比任何其他类型的数据引擎更好地利用该信息,并且它们的查询语言更适合于推理数据中的关系。

虽然在关系数据库中并非不可能,但这些类“好友查询”需要复杂且难以维护,或通过递归CTE或跨许多不同表的复杂联接进行推理。

结论:对于这些类型的问题,请使用图形数据库。

聚合(AGGREGATION)

数据聚合查询是关系数据库的绝佳用例。关系数据库经过优化,可以以最小的开销快速执行复杂的聚合查询。示例问题可能包括:

  1. 我的系统里有多少家公司?
  2. 过去一个月中,我每天的平均销售额是多少?
  3. 我的系统每天处理的事务数量是多少?

这些相同类型的查询可以在图形数据库中执行,便图形遍历的性质要求接触更多的数据。但这会导致更高的查询延迟和资源利用率。

 结论:对于这些类型的问题,使用RDBMS。

模式匹配(PATTERN MATCHING)

基于实体之间如何关联的模式匹配是如何利用图形数据库功能的主要示例。这种查询的典型用例涉及诸如推荐引擎、欺诈检测或入侵检测之类的事情。一些问题可能包括:

  1. 我的系统中谁与我的个人资料相似?
  2. 这笔交易看起来是否与其他已知的欺诈交易类似?
  3. 用户J.Smith和Johan.S是否相同?

模式匹配用例通常在图形数据库中完成,以至于图查询语言具有特定的内置功能,可以精确地处理这类查询。

结论:对于这类型问题,请使用图数据库。

中心性、集群性和影响力(CENTRALITY, CLUSTERING, AND INFLUENCE)

一个实体与另一个实体相比的相对影响程度或重要性是一个典型的图形数据库案例。 一些示例问题可能包括

  1. 谁是我在Linked In上最有影响力的人?
  2. 如果网络中断,我的网络中哪些设备影响最大?
  3. 哪些零件往往同时失效?

此类其他问题的例子包括在Twitter网络中寻找最有影响力的人,确定基础架构的关键部分或在数据中定位实体组。计算此类问题的答案,需要查看实体,它们之间的关系以及事件关系和相邻实体。与模式匹配用例一样,这些类型的问题通常具有特定的内置图形查询语言功能。

结论:对于这些类型的问题,请使用图数据库。

1.2.2 依然很困惑...... 这是图问题吗?

到目前为止讨论的问题类型为确定您的问题是否适合使用图形提供了重要的第一步,但是如果您的问题不完全适合这些预定义类型之一,该怎么办?在本节中,我们将“朋友关系”问题与决策框架结合使用,以帮助我们确定是否使用图数据库问题。

为了说明,我们使用了一个小的社交图,其中包括Alice、Bob、Ted和Josh作为通过follow边连接的顶点,如图1.11所示。 我们要回答的问题是,“给定图中的一个人,他在关注哪些人,这些人又在关注谁,第一个人也可能想要关注?”这个问题与LinkedIn、Twitter或Facebook等网站每天向用户推荐连接的问题相同。 我们将其分为四个基本部分:

  • 给出图中的一个人。。。
  • 。。。他关注的人是哪些。。。
  • 。。。那些人关注的又是谁。。。
  • 。。。第一个人可能也想关注。。。

 

图1.11 一个简单的社交图表说明常见的朋友-朋友关系模式

让我们以鲍勃(Bob)为起点(第一点)。 鲍勃(Bob)关注爱丽丝(Alice)(第二点)。 爱丽丝(Alice)关注泰德(Ted)和乔希(Josh)(第三点)。 因此,鲍勃(Bob)可能想同时关注泰德(Ted)和乔什(Josh)(最后一点)。

 

看看图1.12中的决策树,它旨在回答以下问题:“我应该使用图形数据库吗?”然后我们检查每个问题,并分析为什么这些问题导致您在工作中使用或不使用图形数据库。我们应该从一开始就注意到,这里我们专注于事务(如在线事务处理或OLTP)用例。对于分析用例,决策矩阵可能有所不同(例如在线分析处理或OLAP)。通过第10章,我们几乎专注于事务处理用例,但在最后一章中,我们给也了完整图(或图分析)的一些指导。

图1.12 “我应该使用图形数据库吗?”决策树

  1. 我们是否关心实体之间的关系,而不是实体本身?

这个问题也许是最关键的线索,这就是为什么我们把它放在首位。 它说明了图形数据库最强大的特性之一的核心:关系和实体一样有意义。 如果我们对这个问题的回答是肯定的,那么我们可能需要一个数据模型,它可以使用复杂的关系表示形式,这是使用图形数据库的绝佳选择。 但如果我们的答案是否定的,那么也许另一个数据引擎将是一个更好的选择。

对于我们的朋友问题,这个问题的答案是肯定的。在我们问题的开始步骤(在图中给出一个人)之后,剩下的每一个步骤都需要使用人与人之间的关系来回答。

  1. 我的SQL查询是多表联合(JOIN ON)查询,还是需要递归CTE?

SQL查询语句中大量的联合查询是关系数据库模型设计的特点。当一个SQL查询中使用大量的联合查询语句,那么采用图数据库设计模式是很好的选择。 而且,当这些联合查询不是用来完成带参数检索数据(就像关系数据库中的第三种正常形式所做的那样)而只是用来将实体间链接在一起(就像亲子关系一样)时,我们就应选择图数据库。此外,当我们不知道将要执行的联合查询的数量时,图数据库中的递归查询模式也会立显优势。

以我们的朋友为例,假设我们想要回答以下问题:“从Bob到Ted有什么联系?”试图在关系数据库中执行此未知数量的查询时,得出的结果可能是没有关系,这出乎预料。然而,图数据库可以在无界分层数据上高效地递归。如果递归方法有助于解决问题,那么最好使用图形数据库。

  1. 我的数据结构是否在不断发展

我不会把图数据库称为无模式,这个术语表示数据库引擎不会在写操作上强制执行模式;我们知道几个确实执行模式的图形数据库。但我们可以说,您可以设计图形数据库,以更容忍不断变化的数据结构。 另一方面,关系数据库因其模式的严格性和在进行模式更改时所关联的复杂性而享有当之无愧的声誉。

如果您的问题需要接收具有不同数据模式的数据,例如依赖管理,那么图形数据库可能值得研究。 然而,仅使用数据模式的灵活性不应成为选择图形数据库的充分理由,但与其他功能结合使用,可能足以使规模更小而倾向于使用图形数据库。

  1. 我的实际问题领域适合图吗?

如果您正在做一些事情,如执行路由、依赖管理、社交网络分析或集群分析,那么您的问题将围绕高度互联的数据展开,因此您的领域可能非常适合使用图。提醒一句:虽然你的领域模型自然地适合图,但你的需求不需要对数据中关系进行更多的分析,那你应该考虑其他的数据库。

事实上,早在2014年,我们与图形数据库的最初合作就揭示了客户的数据如何非常自然地适合于图。我们甚至在三个不同的图形数据库中尝试过。该模型具有内置继承功能,循环遍历和依赖分析的自然需求。 客户应用程序中的两个主要数据结构甚至被称为组件(顶点别名)和关系(边别名)。 事实上,它应该建立在一个图形数据库中,而不是一个关系数据库,这对所有的人来说都是显而易见的,他们甚至粗略地查看了数据和域。

最后,这个特定客户的选择不是使用我们评估的三个图形引擎之一,而是更好地使用它们的关系数据库(或者更确切地说,以与它们的主要访问模式一致的方式使用它)。 然后,我们将经过阅读优化的关系投影(基本上遗留模型的完整副本)添加到了关系数据库模式,设计性能查询。有时将其称为命令查询责任隔离(CQRS)模式。有了这种新的“快读”模型,我们证明了他们对某些最苛刻查询的性能提高了100倍。

起初,我们都感到震惊的是,图形数据库没有提供必要的性能改进,因为数据建模是如此自然的一个图形。 然后,我们更仔细地研究了用于评估每个数据库性能的五个查询。 除了继承建模之外,没有任何查询需要图形样式的访问模式。 由于不需要图,我们使用了积极的非规范化来解决继承用例。 事实上,所需的访问模式是非常适合关系数据库;因此,当数据被建模以利用RDBMS查询优化器的优势时,性能显著提高。

回到图形数据库决策树(图1.12);如果您可以对其中一个或多个问题回答“是”,那么图数据库问题。如果使用图数据库仍然存在预知风险,那么设计一个小项目(两天至两周之间)来评估把图数据库作为解决方案的一部分。 此外,切换到使用图形数据库并不一定全有或全无的情况。 不要害怕用图形数据库来解决问题的一部分。 图数据库的多模型方法是常见的,根据我们的经验,往往也是非常成功的。

正如我们在本章开头提到的,关系数据库很好地解决了100个应用程序问题中的88个,所以可以随意使用它们来解决这些问题。 剩下的12个实际上是您可能要开始尝试图形数据库的地方。 本书的其余部分从第2章中的数据建模开始,向您介绍使用图形数据库构建软件的方式。

本章总结:

  1. 图形数据库基于离散数学的图论部分,已有数百年历史了。 这意味着数学家创建了数百年的术语,并不是所有的术语都被认为对使用图数据库构建软件有用或相关。
  2. 图由顶点(也称为节点和实体)和边(也称为关系、链接或连接)组成。边在顶点连接或相交。数据库常见五种类型是键值数据库、列存储数据库、文档型数据库、关系数据库和图数据库。 在这五个数据库中,只有关系数据库和图数据库能够对具有任何复杂程度的关系进行建模。
  3. 图形数据库被设计为具有一流公民身份的关系,从而使构建依赖于这些关系的软件更加容易。当回答严重依赖数据之间关系的问题时,与其他类型的数据库相比,图形数据库的性能往往更好。
  4. 需要递归查询、返回不同结果类型或在实体之间返回路径等应用中图数据库性能更易处理且更容易编码。
  5. 由于图形数据库强大的功能和灵活性,在网上也有大量的优劣图数据库案例。 决定方案是好是坏的最重要的因素是从您选择的任何系统中了解所需的问题和结果。

注:本内容译自《Graph Databases in Action》

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值