我在Neo4j(v2.2.3)中有一个图表,它有2,895,711个节点。在这些节点中,有1,522,166个节点标记为Entity
个节点,其属性名为transactionId
和requestId
。每个属性都包含GUID字符串值。属性未编入索引。 Entity
标签有一个索引属性,名为identifier
唯一,也包含GUID字符串。
我希望将两个现有属性的名称分别更改为updatedTransactionId
和updatedRequestId
。并引入两个名为createdTransactionId
和createdRequestId
的新属性,这些属性将初始化为-unknown-
,但将专门为所有未来的交易设置。
我遇到了对各种 cypher 查询(通过RESTful端点)的指数减慢响应,我试图用它来执行此更新。在处理查询时,我使用PROFILE
指令检查每个查询的计划,以尝试从计划中减少(消除)尽可能多的扫描 尽可能。
以下是分批执行的查询是我最近尝试实现上述结果:
MATCH (e:Entity)
WITH id(e) AS neoId, e.identifier AS identifier ORDER BY neoId SKIP 0 LIMIT 100000
MATCH (n:Entity) WHERE n.identifier = identifier
SET n.updatedRequestId = n.requestId,
n.updatedTransactionId = n.transactionId,
n.createdRequestId = '-unknown-',
n.createdTransactionId ='-unknown-'
REMOVE n.requestId, n.transactionId
RETURN count(n)
每批次增加SKIP
金额,超过16批次。
我发现随着批处理的处理,执行最终会以指数方式变慢。例如,前十个批次按顺序执行以下经过的处理时间(分钟:秒.decimalSeconds),顺序为:00:17.0
,00:09.6
,00:10.1
,00:21.1
,01:22.8
,02:11.0
,03:35.9
,06:12.1
,08:22.2
和11:59.8
。
是否有人对指数性能下降有所解释?而且,更重要的是,建议采用更好的方式来实现上述所需的结果?
感谢阅读。
答案 0 :(得分:1)
每个批次仍然会触及所有Entity
个节点。诀窍是通过为非迁移节点设置标准来避免SKIP
,并将其限制为合理的批量大小。在您的情况下,这可能是requestId
属性的存在。
MATCH (n:Entity)
WHERE HAS(n.requestId)
WITH n LIMIT 100000
SET n.updatedRequestId = n.requestId,
n.updatedTransactionId = n.transactionId,
n.createdRequestId = '-unknown-',
n.createdTransactionId ='-unknown-'
REMOVE n.requestId, n.transactionId
RETURN count(n)
您需要运行此功能,直到返回0
。