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

Java实现文本文件重复项Count列求和的技术咨询

问题分析与解决方案

看起来你是想针对文本文件中的重复项(按RunID或自定义标识)对Count列数值求和,但现有代码的逻辑绕了弯路,既没正确判断重复项,也没实现累加逻辑。我来帮你梳理问题,再给出清晰的实现方案。

你现有代码的核心问题

  1. 逻辑混乱:用两个HashSet判断重复,但没有存储累加的Count值;testt的处理完全无效——循环赋值name却从未使用,导致后续的重复判断都是空架子。
  2. 空值判断错误:data[2].equals(null)会直接抛出NullPointerException,正确写法应该是Objects.isNull(data[2])或data[2] == null。
  3. 资源泄漏风险:Scanner未用try-with-resources自动关闭,异常场景下可能导致资源无法释放。
  4. 缺失累加逻辑:从头到尾没有对Count值做累加操作,仅打印了原始数值。

正确实现思路

核心是用HashMap存储分组键(比如RunID、RunID+Segment,或你需要的文件名子串)和对应的Count总和。步骤如下:

  1. 读取文件并跳过表头行;
  2. 逐行分割数据,提取分组键和Count值;
  3. 用HashMap维护累加:键存在则累加Count,不存在则初始化存入;
  4. 处理完所有行后,输出最终的求和结果。

完整可运行代码

import java.io.File;
import java.io.FileNotFoundException;
import java.util.HashMap;
import java.util.Map;
import java.util.Objects;
import java.util.Scanner;

public class CountSumProcessor {
    public static void main(String[] args) {
        // 替换为你的目标目录路径
        String directoryPath = "your/target/directory";
        File directory = new File(directoryPath);
        File[] filesList = directory.listFiles();
        
        if (filesList == null) {
            System.out.println("指定目录不存在或无法访问");
            return;
        }

        // HashMap:键=分组标识(这里用RunID),值=对应Count的总和
        Map<String, Long> countSumMap = new HashMap<>();

        for (File file : filesList) {
            String filename = file.getName();
            if (!filename.endsWith(".txt")) {
                continue;
            }

            // try-with-resources自动关闭Scanner,避免资源泄漏
            try (Scanner sc = new Scanner(file)) {
                // 跳过表头行
                if (sc.hasNextLine()) {
                    sc.nextLine();
                }

                while (sc.hasNextLine()) {
                    String input = sc.nextLine().trim();
                    if (input.isEmpty()) {
                        continue;
                    }

                    // 按|分割数据,限制为4个字段(避免文件名含|的情况)
                    String[] data = input.split("\\|", 4);
                    if (data.length < 4) {
                        System.out.println("无效行(字段不足):" + input);
                        continue;
                    }

                    String runId = data[0].trim();
                    String countStr = data[2].trim();

                    // 校验空值
                    if (Objects.isNull(runId) || runId.isEmpty() || Objects.isNull(countStr) || countStr.isEmpty()) {
                        System.out.println("无效行(RunID/Count为空):" + input);
                        continue;
                    }

                    // 转换Count为long(避免大数值溢出int)
                    long count;
                    try {
                        count = Long.parseLong(countStr);
                    } catch (NumberFormatException e) {
                        System.out.println("无效Count数值:" + countStr + ",行内容:" + input);
                        continue;
                    }

                    // 累加Count到对应分组
                    countSumMap.put(runId, countSumMap.getOrDefault(runId, 0L) + count);
                }
            } catch (FileNotFoundException e) {
                System.err.println("文件未找到:" + file.getAbsolutePath());
                e.printStackTrace();
            }
        }

        // 输出最终结果
        System.out.println("===== 分组Count求和结果 =====");
        for (Map.Entry<String, Long> entry : countSumMap.entrySet()) {
            System.out.println("RunID: " + entry.getKey() + " | 总Count: " + entry.getValue());
        }
    }
}

关键细节说明

  1. 灵活分组:如果需要按其他维度分组(比如RunID+Segment,或你之前想提取的文件名子串),只需修改键的生成逻辑:
    • 按RunID+Segment分组:
      String key = data[0].trim() + "|" + data[1].trim();
      
    • 按文件名子串(两个下划线之间的部分)分组:
      String fileName = data[3].trim();
      int firstUnderscore = fileName.indexOf("_");
      int secondUnderscore = fileName.indexOf("_", firstUnderscore + 1);
      int lastUnderscore = fileName.lastIndexOf("_");
      if (firstUnderscore != -1 && secondUnderscore != -1 && lastUnderscore != -1) {
          String fileTag = fileName.substring(secondUnderscore + 1, lastUnderscore);
          String key = data[0].trim() + "|" + fileTag;
      }
      
  2. 数据校验:增加了字段长度、空值、数字格式的校验,避免脏数据导致程序崩溃;
  3. 资源安全:用try-with-resources自动管理Scanner,无需手动关闭。

运行你的示例数据后,会得到符合预期的求和结果,比如RunID 6230的总Count为292088+1000000+1000000+1000000=3292088。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.04.30 14:32:52