You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Java实现数组中连续重复n次数字提取:传统与Stream方式

提取数组中连续重复恰好n次的元素(Java实现)

问题背景

给定数组:

int[] nums = {1, 1, 1, 2, 2, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 1, 1, 2, 2, 2};

需求是提取数组中连续重复恰好n次的数字。比如当n=3时,结果应该是1、3、5、2;而连续重复4次的4不符合要求,不能纳入结果。

下面这段尝试的代码存在问题:循环条件i < nums.length - 3会忽略数组最后三个元素,取消这个限制又会触发数组越界:

for(int i = 0; i < nums.length - 3; i++) {
    if(nums[i] == nums[i + 1] && nums[i + 1] == nums[i + 2] && nums[i + 2] != nums[i + 3]) {
        System.out.println(nums[i]);
        continue;
    }
}

解决方案

1. 传统循环实现

核心思路是遍历数组,实时统计当前元素的连续重复次数。当遇到不同元素或者遍历到数组末尾时,检查当前统计的次数是否恰好等于n,符合条件就把该元素加入结果列表。

import java.util.ArrayList;
import java.util.List;

public class ConsecutiveDuplicateExtractor {
    public static void main(String[] args) {
        int[] nums = {1, 1, 1, 2, 2, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 1, 1, 2, 2, 2};
        int targetCount = 3;
        List<Integer> result = new ArrayList<>();

        if (nums.length == 0) {
            System.out.println(result);
            return;
        }

        int currentNum = nums[0];
        int consecutiveCount = 1;

        for (int i = 1; i < nums.length; i++) {
            if (nums[i] == currentNum) {
                consecutiveCount++;
            } else {
                // 切换元素时,检查上一组的连续次数
                if (consecutiveCount == targetCount) {
                    result.add(currentNum);
                }
                currentNum = nums[i];
                consecutiveCount = 1;
            }
        }

        // 处理数组最后一组连续元素
        if (consecutiveCount == targetCount) {
            result.add(currentNum);
        }

        System.out.println("符合条件的元素:" + result); // 输出 [1, 3, 5, 2]
    }
}

2. Java 8 Stream实现

这里提供两种Stream写法,第一种是结合遍历统计的直观实现,第二种更偏向函数式风格:

写法一:基于遍历统计的Stream实现

利用IntStream遍历数组,用数组保存当前元素和连续次数(因为lambda表达式中无法修改局部变量,所以用数组作为容器):

import java.util.ArrayList;
import java.util.List;
import java.util.stream.IntStream;

public class StreamConsecutiveExtractor {
    public static void main(String[] args) {
        int[] nums = {1, 1, 1, 2, 2, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 1, 1, 2, 2, 2};
        int targetCount = 3;
        List<Integer> result = new ArrayList<>();

        if (nums.length == 0) {
            System.out.println(result);
            return;
        }

        // current[0] = 当前元素,current[1] = 连续次数
        int[] current = {nums[0], 1};

        IntStream.range(1, nums.length)
                .forEach(index -> {
                    if (nums[index] == current[0]) {
                        current[1]++;
                    } else {
                        if (current[1] == targetCount) {
                            result.add(current[0]);
                        }
                        current[0] = nums[index];
                        current[1] = 1;
                    }
                });

        // 处理最后一组元素
        if (current[1] == targetCount) {
            result.add(current[0]);
        }

        System.out.println("符合条件的元素:" + result); // 输出 [1, 3, 5, 2]
    }
}

写法二:函数式分组的Stream实现

通过Stream.iterate生成连续重复元素的分组(每个分组包含元素和连续次数),再过滤出次数符合要求的元素:

import java.util.List;
import java.util.stream.Collectors;
import java.util.stream.Stream;

public class FunctionalStreamExtractor {
    public static void main(String[] args) {
        int[] nums = {1, 1, 1, 2, 2, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 1, 1, 2, 2, 2};
        int targetCount = 3;

        if (nums.length == 0) {
            System.out.println(List.of());
            return;
        }

        // 生成连续重复分组:每个分组是 [当前索引, 元素值, 连续次数]
        Stream<int[]> consecutiveGroups = Stream.iterate(
                new int[]{0, nums[0], 1},
                state -> state[0] < nums.length - 1 ?
                        (nums[state[0] + 1] == state[1] ?
                                new int[]{state[0] + 1, state[1], state[2] + 1} :
                                new int[]{state[0] + 1, nums[state[0] + 1], 1}) :
                        null
        ).takeWhile(state -> state != null);

        // 过滤出连续次数等于targetCount的元素
        List<Integer> result = consecutiveGroups
                .filter(group -> group[2] == targetCount)
                .map(group -> group[1])
                .collect(Collectors.toList());

        System.out.println("符合条件的元素:" + result); // 输出 [1, 3, 5, 2]
    }
}

内容的提问来源于stack exchange,提问作者barry allen

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.04 14:25:20