【问题标题】:Graph Database Newbie Q- How to decide on the direction of a relation between 2 nodes图数据库新手Q-如何确定2个节点之间关系的方向
【发布时间】:2016-11-10 15:46:50
【问题描述】:

你如何决定关系的动词方向?

例如,我有一个国家属于一个子区域,而该子区域又属于一个区域。 哪个更好,在决定方向上有什么经验法则。

(区域)-[HAS]->(子区域)-[HAS]->(国家)

(地区)

问候 圣

【问题讨论】:

  • 这几乎是一个纯粹的主观问题,我可以看到这个问题因此而被关闭。它归结为对您的领域最有意义的东西,并且适合您对建模所需的任何程度的模糊性或特异性。由于 Neo4j 很灵活,您没有理由不能暂时尝试一种方式,如果您觉得另一种方式更好,请使用 APOC 程序重构调用来更改关系类型和/或方向。
  • 这真的归结为这个方向意味着什么。当您说国家属于一个子区域时,子区域可以属于一个国家吗?如果是这种情况,那么一个方向可能是有意义的。如果不是,则根本不要使用方向,因为这不是可能的情况。避免方向是一种很好的做法,因为它消除了查询中的大量复杂性。您也可以将语义移至边缘标签。

标签: database graph neo4j


【解决方案1】:

我同意@InverFalcon 的观点,即方向性主要是一个主观决定。但是,可能存在(至少)一种情况,您可能希望使用特定的方向,特别是如果这会使重要的用例更快。

这与以下事实有关:如果您通常可以使 Cypher 模式不那么具体(不影响输出),那么 neo4j 将不得不做更少的工作并且您的查询会更快。

例如,假设您的整个数据模型包含 2 个节点标签和 2 个关系类型,如下所示。 (我使用自己的数据模型,因为我不知道您的用例是什么。)

(:Person)-[:ACTED_IN]->(:Movie)
(:Person)-[:DIRECTED]->(:Movie)

为了找到某个演员出演的电影,您的查询必须类似于以下内容。 (注意,我们必须指定ACTED_IN 类型,因为传出关系也可以是DIRECTED 类型。这意味着neo4j 必须显式测试每个传出关系的类型):

MATCH (:Person {id: 123})-[:ACTED_IN]->(m:Movie)
RETURN m;

但是,如果您的数据模型将 DIRECTED 类型替换为具有相反方向性的 DIRECTED_BY 类型,那么它会变成这样:

(:Person)-[:ACTED_IN]->(:Movie)
(:Person)<-[:DIRECTED_BY]-(:Movie)

通过该调整,您的查询可以更简单、更快(因为 neo4j 不必测试关系类型):

MATCH (:Person {id: 123})-->(m:Movie)
RETURN m;

为了完整起见,请注意在上述 2 个MATCH 模式中,我们实际上可以删除:Movie 标签,因为在两个数据模型中,ACTED_IN 端节点将始终具有Movie 标签.

【讨论】:

  • 只是为了回答的完整性;不应删除 Person 标签,否则 Neo4j 将在所有节点中搜索 id: 123 。删除标签只会在上述确切情况下加快速度 - MATCH (:Person {id: 123})-->(m:Movie) RETURN m;
猜你喜欢
  • 1970-01-01
  • 2020-08-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-06-05
  • 1970-01-01
  • 2019-07-15
相关资源
最近更新 更多