Neo4j数据导入速度慢

问题描述

我必须在Neo4j DB中加载大约5M条记录,所以我将excel分解为以表格格式显示的100K数据块,为此我正在使用CyperShell,但似乎已经超过8个小时了,而且仍然卡在第一块上

我正在使用

USING PERIODIC COMMIT
LOAD CSV WITH HEADERS from 'file://aa.xlsx' as row
MERGE (p1:L1 {Name: row.sl1})
MERGE (p2:L2 {Name: row.sl2})
MERGE (p3:L3 {Name: row.sl3,Path:row.sl3a})
MERGE (p4:L4 {Name: row.sl4})
MERGE (p5:L4 {Name: row.tl1})
MERGE (p6:L3 {Name: row.tl2})
MERGE (p7:L2 {Name: row.tl3,Path:row.tl3a})
MERGE (p8:L1 {Name: row.tl4})
MERGE (p1)-[:s]->(p2)-[:s]->(p3)-[:s]->(p4)-[:it]->(p5)-[:t]->(p6)-[:t]->(p7)-[:t]->(p8)

任何人都可以建议我进行更改或替代方法以更快的方式加载数据

Excel格式的数据

enter image description here

解决方法

  1. 要导入大量数据,应考虑使用import工具而不是Cypher的LOAD CSV子句。该工具只能导入以前未使用的数据库。

  2. 如果您仍然想使用LOAD CSV,则需要进行一些更改。

    • 您未正确使用MERGE,因此可能会生成许多重复的节点和关系。您可能会发现this answer具有启发性。

      如果其中有任何内容,则会创建一个MERGE子句的整个模式 该模式尚不存在。

      因此,您的最后一个MERGE模式及其七个关系特别危险。应该将其分为七个具有各自关系的MERGE子句。

      此外,指定多个属性的MERGE模式也可能是不好的。例如,如果所有L3节点都具有唯一的Name值,则替换该值将更安全:

      MERGE (p3:L3 {Name: row.sl3,Path:row.sl3a})
      

      具有以下类似内容:

      MERGE (p3:L3 {Name: row.sl3})
      ON CREATE SET p3.Path = row.sl3a
      

      在以上代码段中,如果该节点已经存在,但是row.sl3a与现有的Path值不同,则不会创建其他节点。另外,由于该节点已经存在,因此ON CREATE选项不会执行其SET子句,从而使原始Path值保持不变。您也可以选择改用ON MATCH,或者无论如何设置值,直接直接调用SET

    • 为避免每次MERGE需要查找现有节点时都必须扫描具有给定标签的所有节点,您应该为每个节点创建一个indexuniqueness constraintMERGE的每个节点的标签/属性对:

      • :L1(Name)
      • :L2(Name)
      • :L3(Name)
      • :L4(Name)