我正在编写一个 api 来返回 neo4j 数据。对于我的情况,我得到所有匹配的节点。API 接受 userId、limit 和 offset 并返回符合该条件的数据列表。
我找到了一个解决方案Cypher 来返回总节点数以及有限的集合,但它相当旧。不确定这是否仍然是最好的方法。
性能与触发 2 个单独的查询相同,至少其中一个查询在几次运行后会被 Neo4j 缓存。
Match(u:WorkstationUser {id: "alw:44807"})-[:HAS_ACCESS_TO]->(p) return distinct(p) skip 0 limit 10
Match(u:WorkstationUser {id: "alw:44807"})-[:HAS_ACCESS_TO]->(p) return count(distinct(p))
Run Code Online (Sandbox Code Playgroud)
我希望结果是这样的
{
items: [ {}, {}], # query 1
total: 100, # query 2
limit: 10, # can get from input
skip: 0 # can get from input
}
Run Code Online (Sandbox Code Playgroud)
这在一定程度上取决于您需要从想要计数的节点获得多少信息,以及您是否需要获得不同的结果。
如果不需要不同的结果,并且不需要对另一端的关系或节点进行任何额外的过滤(不过滤节点的标签或属性),那么您可以使用模式将使用节点上存在的关系的度信息,这更有效,因为您不必实际扩展关系:
MATCH (u:WorkstationUser {id: "alw:44807"})
WITH u, size((u)-[:HAS_ACCESS_TO]->(p)) as total
MATCH (u)-[:HAS_ACCESS_TO]->(p)
RETURN p, total
SKIP 0 LIMIT 10
Run Code Online (Sandbox Code Playgroud)
但是,如果需要不同的结果,或者需要按标签或属性过滤节点,则必须展开所有结果才能获得总数。如果没有太多结果(数百万或数十亿),那么您可以收集不同的节点,获取集合的大小,然后展开结果和页面:
MATCH (:WorkstationUser {id: "alw:44807"})-[:HAS_ACCESS_TO]->(p)
WITH collect(DISTINCT p) as pList
WITH pList, size(pList) as total
UNWIND pList as p
RETURN p, total
SKIP 0 LIMIT 10
Run Code Online (Sandbox Code Playgroud)