Neo4j 匹配和创建在 10000 节点图中花费的时间太长
Neo4j Match and Create takes too long in a 10000 node graph
我有一个这样的数据模型:
- 人物节点
- 电子邮件节点
- OWNS 关系
- LISTS 关系
- 知道关系
每个人可以拥有一个电子邮件并列出多个电子邮件(如联系人列表,假设每个人有 200 个联系人)。
我正在尝试执行的查询是找到所有拥有联系人列表的电子邮件的人,并在他们之间创建 KNOWS 关系。
MATCH (n:Person {uid:'123'}) -[r1:LISTS]-> (m:Email) <-[r2:OWNS]- (l:Person)
CREATE UNIQUE (n)-[:KNOWS]->[l]
我当前数据库的计数如下:
- 人物节点数:10948
- 邮件节点数:1951481
- OWNS 关系数:21882
- LISTS 关系数:4376340(每个人有 200 个不同的 LISTS 关系)
现在我的问题是 运行 对当前数据库的上述查询需要 4.3 到 4.8 秒之间的时间,这对我的需要来说是不可接受的。我想知道考虑到我的数据模型,这是否是正常时间,还是我对查询(甚至模型)做错了什么。
如有任何帮助,我们将不胜感激。另外,如果这对 Neo4j 来说是正常的,请随时建议可以更好地处理这种模型的其他图形数据库。
非常感谢您
更新:
我的查询是:profile match (n: {uid: '4692'}) -[:LISTS]-> (:Email) <-[:OWNS]- (l) create unique (n)-[r:KNOWS]->(l)
我的查询中的 PROFILE 命令 returns 这个:
Cypher version: CYPHER 2.2, planner: RULE. 3919222 total db hits in 2713 ms.
是的,需要 4.5 秒才能从索引中匹配一个人及其 <=100 个列出的电子邮件地址,并将用户与每封电子邮件的单个所有者的关系合并,这很慢。
首先要确保在带有 :Person
标签的节点上有 uid
属性 的索引。使用 SCHEMA
命令检查您的索引,如果缺少,请使用 CREATE INDEX ON :Person(uid)
.
创建这样的索引
其次,CREATE UNIQUE
可能会或可能不会很好地完成工作,但您会希望改用 MERGE
。 CREATE UNIQUE
已弃用,尽管它们有时是等价的,但您要执行的操作应该用 MERGE
.
表示
第三,要找出查询缓慢的原因,您可以分析它:
PROFILE
MATCH (n:Person {uid:'123'})-[:LISTS]->(m:Email)<-[:OWNS]-(l:Person)
MERGE (n)-[:KNOWS]->[l]
有关详细信息,请参阅 1, 2。您可能还想分析您的查询,同时强制使用一个或另一个基于成本和规则的查询规划器来比较他们的计划。
CYPHER planner=cost
PROFILE
MATCH (n:Person {uid:'123'})-[:LISTS]->(m:Email)<-[:OWNS]-(l:Person)
MERGE (n)-[:KNOWS]->[l]
有了这些,您有望找到并更正问题,或者使用信息更新您的问题,以帮助其他人帮助您找到问题。
我有一个这样的数据模型:
- 人物节点
- 电子邮件节点
- OWNS 关系
- LISTS 关系
- 知道关系
每个人可以拥有一个电子邮件并列出多个电子邮件(如联系人列表,假设每个人有 200 个联系人)。
我正在尝试执行的查询是找到所有拥有联系人列表的电子邮件的人,并在他们之间创建 KNOWS 关系。
MATCH (n:Person {uid:'123'}) -[r1:LISTS]-> (m:Email) <-[r2:OWNS]- (l:Person)
CREATE UNIQUE (n)-[:KNOWS]->[l]
我当前数据库的计数如下:
- 人物节点数:10948
- 邮件节点数:1951481
- OWNS 关系数:21882
- LISTS 关系数:4376340(每个人有 200 个不同的 LISTS 关系)
现在我的问题是 运行 对当前数据库的上述查询需要 4.3 到 4.8 秒之间的时间,这对我的需要来说是不可接受的。我想知道考虑到我的数据模型,这是否是正常时间,还是我对查询(甚至模型)做错了什么。
如有任何帮助,我们将不胜感激。另外,如果这对 Neo4j 来说是正常的,请随时建议可以更好地处理这种模型的其他图形数据库。
非常感谢您
更新:
我的查询是:profile match (n: {uid: '4692'}) -[:LISTS]-> (:Email) <-[:OWNS]- (l) create unique (n)-[r:KNOWS]->(l)
我的查询中的 PROFILE 命令 returns 这个:
Cypher version: CYPHER 2.2, planner: RULE. 3919222 total db hits in 2713 ms.
是的,需要 4.5 秒才能从索引中匹配一个人及其 <=100 个列出的电子邮件地址,并将用户与每封电子邮件的单个所有者的关系合并,这很慢。
首先要确保在带有 :Person
标签的节点上有 uid
属性 的索引。使用 SCHEMA
命令检查您的索引,如果缺少,请使用 CREATE INDEX ON :Person(uid)
.
其次,CREATE UNIQUE
可能会或可能不会很好地完成工作,但您会希望改用 MERGE
。 CREATE UNIQUE
已弃用,尽管它们有时是等价的,但您要执行的操作应该用 MERGE
.
第三,要找出查询缓慢的原因,您可以分析它:
PROFILE
MATCH (n:Person {uid:'123'})-[:LISTS]->(m:Email)<-[:OWNS]-(l:Person)
MERGE (n)-[:KNOWS]->[l]
有关详细信息,请参阅 1, 2。您可能还想分析您的查询,同时强制使用一个或另一个基于成本和规则的查询规划器来比较他们的计划。
CYPHER planner=cost
PROFILE
MATCH (n:Person {uid:'123'})-[:LISTS]->(m:Email)<-[:OWNS]-(l:Person)
MERGE (n)-[:KNOWS]->[l]
有了这些,您有望找到并更正问题,或者使用信息更新您的问题,以帮助其他人帮助您找到问题。