如何在Neo4j中将带间隔的有序整数集合拆分为连续范围?
在Neo4j中把带间隔的有序整数集合转换为连续范围集合
可以通过Cypher的窗口函数(LAG、SUM OVER)实现类似map/reduce的分组逻辑,将连续整数归为一组后聚合生成范围字符串,具体步骤如下:
核心逻辑
- 将有序集合拆分为单个元素,逐个对比相邻元素的差值;
- 标记差值大于1的位置为新分组起点;
- 通过累加标记值生成分组ID,把连续元素归为同一组;
- 按分组ID聚合,取每组的最小/最大值拼接成范围格式。
完整Cypher示例
// 替换为你的有序整数集合(比如聚合查询结果) WITH [1,2,3,4,5,7,8,9,10,45,46,47,48] AS nums UNWIND nums AS num // 标记新分组起点:第一个元素 或 当前元素与前一个差值>1 WITH num, CASE WHEN LAG(num) OVER () IS NULL OR num - LAG(num) OVER () > 1 THEN 1 ELSE 0 END AS is_new_group // 累加标记生成分组ID,连续元素将获得相同ID WITH num, SUM(is_new_group) OVER (ORDER BY num) AS group_id // 按分组聚合,获取每个连续范围的起止值 WITH group_id, MIN(num) AS range_start, MAX(num) AS range_end // 生成最终范围字符串,单元素范围直接显示数字 RETURN COLLECT( CASE WHEN range_start = range_end THEN toString(range_start) ELSE toString(range_start) + "-" + toString(range_end) END ) AS continuous_ranges
适配数据库查询场景
如果你的整数集合是从数据库节点/关系中聚合得到的,只需替换初始的WITH语句即可,比如从SomeNode节点的id属性获取有序集合:
MATCH (n:SomeNode) // 确保集合有序,需在COLLECT前加ORDER BY WITH COLLECT(n.id ORDER BY n.id) AS nums UNWIND nums AS num WITH num, CASE WHEN LAG(num) OVER () IS NULL OR num - LAG(num) OVER () > 1 THEN 1 ELSE 0 END AS is_new_group WITH num, SUM(is_new_group) OVER (ORDER BY num) AS group_id WITH group_id, MIN(num) AS range_start, MAX(num) AS range_end RETURN COLLECT( CASE WHEN range_start = range_end THEN toString(range_start) ELSE toString(range_start) + "-" + toString(range_end) END ) AS continuous_ranges
内容的提问来源于stack exchange,提问作者remort
相关产品推荐
相关产品推荐

