嵌入式neo4j:遍历大图的所有节点

时间:2015-11-16 18:34:45

标签: neo4j neo4j-embedded

我想迭代~100Mio图中的所有节点。我知道我可以用cypher-query

获取节点
    MATCH n RETURN n

但是我必须使用LIMIT和SKIP自己完成数据集,我认为这种方法存在性能问题。

现在我的问题是:如何使用嵌入式neo4j数据库迭代所有节点?整个事情将是一个后台工作(索引节点到elasticsearch)。

2 个答案:

答案 0 :(得分:4)

感谢大家提到GraphAware,只是为了让另一种方法融入其中:获得所有节点的问题是{@ 1}}所有节点都发生在单个事务中。在具有100M节点的图形上,这将不起作用。

出于这个原因,GraphAware Framework有许多BatchTransactionExecutor我们在我们的模块中用于重新索引/恢复以及需要为每个节点/关系执行某些操作的场景或其中一部分。

让我发一个如何使用它的例子 - 它来自GraphAware的Schema Enforcement Module(非开源,因此在这里发布):

GlobalGraphOperations

大多数输入参数应该是不言自明的。请注意,AllNodes是另一个框架类,它按照每个事务以1000(在这种情况下)批量从 final List<String> violations = new LinkedList<>(); new IterableInputBatchTransactionExecutor<>(database, 1000, new AllNodes(database, 1000), new UnitOfWork<Node>() { @Override public void execute(GraphDatabaseService database, Node input, int batchNumber, int stepNumber) { for (Constraint<Node> constraint : nodeConstraints) { if (!constraint.satisfiedBy(input)) { violations.add(input + " violates " + constraint.toString()); } } } }).execute(); 获取所有节点。我们提供其他人(databaseAllNodesWithLabel),但您可以轻松实现自己的。

在后台执行此操作是创建单独的线程的问题,或者如果您想要更复杂,请使用框架的计时器驱动模块,正如William已经指出的那样。

答案 1 :(得分:3)

由于您提到您使用的是嵌入式Neo4j,因此您可能希望使用文档here而不是Cypher来使用Java API。

具体而言,课程GlobalGraphOperations提供了getAllNodes()方法,记录为here

for (Node node : GlobalGraphOperations.at(db).getAllNodes()) {
  // Do something with the node here
}

修改

要考虑的其他几点:

  1. 您可以实现transaction hook handler以在插入/更新节点时启动Elasticsearch索引操作,而不是迭代数据库中的所有节点。
  2. 如果您希望此操作在后台定期运行,您可能需要考虑使用GraphAware framework's计时器驱动runtime module。此插件提供了一个运行时,用于在后台定期执行操作,并可配置为在数据库负载增加时缩减。