Neo4j 中的收集速度非常慢

Collect is very slow in Neo4j

如何在 2.2B 节点上使用集合汇总一对带有标签的 ID?我想滚动两个 uid 的平面列表,标签连接它们而不重复。 我在 neo4j 中有一个图表,由 10 个 ID、9 个连接 ID 和 1 个第一方 ID 组成。

我正在尝试为由一个或多个连接 ID 连接的每一对第一方 ID 创建一个查询,我有一个连接它们的第三方 ID 的列表。

现在我有一个查询如下:

Match (u:User)-[]->(id)
match (id)<-[]-(u2:User)
where u <> u2 and ID(u) < ID(u2)
return u.uid,u2.uid,labels(id)
limit 100

which returns u, u1, 标签的列表,看起来像

u|u2|labels
uid1|uid2|["label1"] 
uid2|uid3|["label2"]
uid1|uid2|["label2"]

我想做的是将列表汇总到一个集合中,类似

Match (u:User)-[]->(id)
match (id)<-[]-(u2:User)
where u <> u2 and ID(u) < ID(u2)
return u.uid,u2.uid,collect(labels(id))
limit 100

但是它非常慢并且冻结了我的浏览器。我正在 244 GB EC2 上处理 163GB 数据集,并给出了

dbms.memory.heap.initial_size=150g
dbms.memory.heap.max_size=150g
dbms.memory.pagecache.size=60g

问题是 collect() 聚合将要求所有结果首先具体化,因此 LIMIT 将只是最后的过滤器,这不适用于您的数据库的大小。

由于您的限制应该仅适用于具有该模式的不同节点对(无论它们之间有多少公共节点),最好将 LIMIT 向上移动并在之后找到它们(及其标签)之间的公共节点您正在使用有限的 100 个。

试一试:

MATCH (u:User)-->()<--(u2:User)
WHERE ID(u) < ID(u2)
WITH DISTINCT u, u2
LIMIT 100
RETURN u, u2, [(u)-->(id)<--(u2) | labels(id)] as idLabels

我们在最后使用模式理解,但您可以轻松完成 MATCH 和 collect()。