2016-05-03 85 views
0

我有图:(:Sector)<-[:BELONGS_TO]-(:Company)-[:PRODUCE]->(:Product)Neo4j/Cypher匹配遍历分支中的前n个节点

我在查找以下查询。

开始于(:Sector)。然后匹配该部门的前50家公司,并为每家公司匹配前10个产品。

第一个限制很简单。但是限制产品呢。

cypher可能吗?

UPDATE

由于@cybersam建议如下查询将返回有效的结果

MATCH (s:Sector)<-[:BELONGS_TO]-(c:Company) 
WITH c 
LIMIT 50 
MATCH (c)-[:PRODUCE]->(p:Product) 
WITH c, (COLLECT(p))[0..10] AS products 
RETURN c, products 

但是这种解决方案不能扩展,因为它依然穿越每家公司的所有产品。收集每个公司产品后应用切片。随着产品数量的增长,查询性能会下降。

回答

1

此查询的每个返回行包含:一个部门,其企业(最多50每扇区)中的一个,和高达10个产品为公司的集合:

MATCH (s:Sector)<-[:BELONGS_TO]-(c:Company) 
WITH s, (COLLECT(c))[0..50] AS companies 
UNWIND companies AS company 
MATCH (company)-[:PRODUCE]->(p:Product) 
WITH s, company, (COLLECT(p))[0..10] AS products; 
+1

欢呼@cybersam。这个查询起作用。但如果每家公司的产品数量增长,它将如何扩展?你仍然会匹配所有产品,将它们分组并限制后。我有兴趣是否可以在匹配一定数量的节点时停止匹配。 – drgraduss

+0

这是一个很好的问题。不幸的是,我没有看到使用'LIMIT'的方法,因此它只限制每个公司的产品。 – cybersam

+0

好的。似乎Traversal Framework API是我的答案。我将接受有关可伸缩性的说明。感谢您的帮助@cybersam。 – drgraduss

1

更新一些解决方案使用APOC Procedures

这篇关于limiting results per row的Neo4j知识库文章介绍了几种不同的方法来完成此操作。

一种方法是使用apoc.cypher.run()每行执行有限的子查询。适用于有问题的查询,这会工作:

MATCH (s:Sector)<-[:BELONGS_TO]-(c:Company) 
WITH c 
LIMIT 50 
CALL apoc.cypher.run('MATCH (c)-[:PRODUCE]->(p:Product) WITH p LIMIT 10 RETURN collect(p) as products', {c:c}) YIELD value 
RETURN c, value.products AS products 

使用APOC路径扩展程序,在终端过滤和限制,提供标签中提到的其他替代:

MATCH (s:Sector)<-[:BELONGS_TO]-(c:Company) 
WITH c 
LIMIT 50 
CALL apoc.path.subgraphNodes(c, {maxLevel:1, relationshipFilter:'PRODUCE>', labelFilter:'/Product', limit:10}) YIELD node 
RETURN c, collect(node) AS products