【问题标题】:Neo4j graph modelling performance and querability, property to a node or as separate node plus relationshipNeo4j 图形建模性能和可查询性、属性到节点或作为单独的节点加关系
【发布时间】:2015-08-01 19:39:52
【问题描述】:

我正在自学图形建模并使用带有 NodeJs 和 Express 框架的 Neo4j 2.2.3 数据库。

我浏览了免费的neo4j图形数据库书,学习了如何建模场景、何时使用关系以及何时创建节点等。

我已经建模了一个汽车销售场景,具有以下结构

节点

(:VEHICLE{mileage:xxx, manufacture_year: xxxx, price: xxxx})
(:VFUEL_TYPE{type:xxxx}) x 2 (one for diesel and one for petrol)
(:VCOLOR{color:xxxx}) x 8 (red, green, blue, .... yellow) 
(:VGEARBOX{type:xxx}) x 2 (AUTO, MANUAL) 

关系

(vehicleNode)-[:VHAVE_COLOR]->(colorNode - either of the colors)
(vehicleNode)-[:VGEARBOX_IS]->(gearboxNode - either manual or auto)
(vehicleNode)-[:VCONSUMES_FUEL_TYPE]->(fuelNode - either diesel or petrol)

假设我们具有上述结构,其余功能依此类推。

如上面的屏幕截图所示(136 和 137 是 VEHICLE 节点),车辆的大部分特征被创建为单独的节点,并在具有共同特征的车辆之间共享。

您能否建议颜色、车身类型、驾驶侧(左驱动或右驱动)、变速箱等角色(标签)应该是单独的节点还是车辆节点的属性?哪个选项对性能更友好且易于查询?

我想编写一个 JS 代码,允许使用一个或多个搜索条件查询具有上述结构的图形。如果这些特征中的大多数是 VEHICLE 节点的属性,那么查询就不难了:

MATCH (v:VEHICLE) WHERE v.gearbox = "MANUAL" AND v.fuel_type = "PETROL" AND v.price > x AND v.price < y AND .... RETURN v; 

但是,对于我拥有的现有图形模型,搜索起来很棘手,特别是当有多个条件不一定是 VEHICLE 节点的属性而是单独的节点并通过关系链接时。

任何关于图形现有结构的想法和建议,以使其更易于查询和性能友好,我们将不胜感激。如果我们想象一个有 1000 个 VEHICLE 节点的场景会产生 15000 个关系,听起来有点吓人,如果它达到 100 万个 VEHICLE,那么最多有 1500 万个关系。如果我朝错误的方向前进,请发表评论。

感谢您的宝贵时间。

【问题讨论】:

  • 我正在开发一个类似的模型......这对你来说效果好吗?

标签: neo4j


【解决方案1】:

建模充满了权衡,看起来你有一个不错的开始。

根本不用关心关系的数量。这就是图数据库擅长的,所以我不会太担心过度使用它们。

应该是属性还是节点?我无法回答您的情况,但这里有一些需要考虑的事项:

  • 如果您一直按一个值查找某个对象,并且您有很多对象,那么找到一个节点然后找到与之相连的所有对象通常会更快,因为图 DB 擅长利用关系。扫描标签的所有节点并查找属性=值的项目的速度较慢。
  • 当您想要表达与非简单原始数据类型的连接时,关系可以很好地工作。例如,以“变速箱”为例。有手册和其他类型......如果它是一个属性值,您以后将无法轻易决定存储“齿轮箱”的其他 4 个子类型/子方面。如果它是一个节点,那以后会很容易,因为您可以向该节点添加更多属性,或关联其他事物。
  • 如果一条数据确实是一个原始数据(字符串、整数等)并且您不需要关于它的额外细节,这通常是一个很好的属性。稍后通过连接到其他节点来查询原始值会显得很笨拙。例如,我不会将具有“出生日期”的人建模为单独的节点,这会让人难以查询,并且会为您提供将来不太可能需要的灵活性。
  • 从语义上讲,您的数据是如何相关的?如果两个项目是相似的,因为它们共享一个 X,那么那个 X 可能应该是一个节点。如果两个项目碰巧具有相同的 Y 值,但实际上并没有多大意义,那么将 Y 作为节点属性可能会更好。

【讨论】:

  • 我认为绝对有可能建立太多的关系。不是因为 Neo4j 无法处理它,而是因为它开始增加查询的复杂性。在很多情况下,如果值非常简单,我建议从属性开始。如果您愿意,可以轻松迁移数据并在以后创建节点。
  • 另外,当您说为标签搜索属性通常比先查找节点然后查找它的关系要慢时,当标签/属性组合具有索引时是否如此?我怀疑它会根据图表的大小和不同部分的关系密度而有所不同。
  • 一切都取决于数据量和查询模式。在不知道这些事情的情况下,我认为没有关于什么更快的具体答案。是的 - 我同意您可以过度创建关系以使您的查询复杂化。
  • 很难提供关于何时属性/何时关系的确切答案。因此,取而代之的是关于“什么会暗示财产”、“什么会暗示关系”的一般规则。尽管取决于查询负载/数据量,但一切都是可延展的
  • 感谢@FrobberOfBits 的详细解释。就数据的连通性而言,基本上假设有人想要 - 一辆宝马、柴油和手动变速箱和 2.1 发动机尺寸的车辆,红色,2002 年制造,里程 x ,价格在 y 和 z 之间。 ......图表应该返回所有符合条件的节点。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多