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

Java并发导致数据混淆求助:多线程读文件出现异常数据

线程文件读取数据串流异常排查求助

现有两个线程通过readFileByBuffer方法读取文本文件:线程A读取内容全为“a”的文件,线程B读取内容全为“b”的文件,但checkLine方法偶尔会检测到数据异常。打印数据后发现线程A读取到混合数据(如aaaaaaaaaaaaaaaaaaaaaaaaaabbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb)。该问题难以复现,且仅在将Linux内核从3.10升级到4.19后出现,尝试升级OpenJDK并未解决问题,恳请提供排查建议。

相关代码如下:

public boolean readFileByBuffer(String fileName){
    public boolean run(String fileName) {
            try(BufferedReader br = NewIoUtils.newBufferedReader(new FileReader(fileName))){
                String readLine ;
                while((readLine = br.readLine()) != null){
                    checkLine(readLine);
            }
                return true;
            }catch (FileNotFoundException e){
                System.out.printf("can't found file , fileName :%s ,异常",fileName );
            }catch(Exception e){
                System.out.printf("Reading file exception :fileName : %s ,异常",fileName );
            }
            return false;
        }

    public boolean checkLine(String line){
        if(StringUtils.isBlank(line))
        {
            log.error("The current line does not exist,projectCode:() ,batchId:()",projectCode,transBatchId);
            return false;
        }
        List<String> contents = CheckConfigUtils.getSplitLine(line);
        if (contents == null|| contents.size() < fieldCount)
        {
            log.error("Check that the number of fields is less than the configured number");
            return false;
        }
    }

}

排查建议

  • 优先检查NewIoUtils.newBufferedReader的实现:确认该工具类是否存在线程不安全设计,比如复用全局缓冲区、Reader实例,或未正确隔离不同线程的IO资源。若多个线程共享同一个BufferedReader的底层缓冲区,必然会导致数据串流。
  • 验证文件完整性:读取前对目标文件计算哈希值(如MD5、SHA-1),确认线程A读取的文件确实全为“a”,排除文件被其他进程意外写入的可能。
  • 测试替换JDK原生IO实现:暂时用JDK原生的new BufferedReader(new FileReader(fileName))替换NewIoUtils的实现,若问题消失,说明自定义工具类存在适配问题。
  • 增加线程级追踪日志:给每个线程添加唯一标识,读取文件时打印线程ID、文件名、读取行的内容及哈希值,一旦出现异常即可精准定位数据来源。
  • 排查Linux内核IO相关配置:4.19内核在文件缓存、IO调度上有较多改动,可检查vm.dirty_ratio、vm.dirty_background_ratio等内存缓存参数,或尝试挂载文件系统时添加noatime/nodiratime参数,排查缓存一致性问题。
  • 检查文件描述符与锁机制:用lsof命令在问题出现时查看文件的打开进程,确认是否有其他进程对文件加锁或共享文件句柄;同时检查系统的文件描述符限制是否足够。
  • 调整JVM IO参数:尝试添加JVM参数禁用部分IO优化,比如-Dsun.nio.disableSystemWideOverlappingFileLockCheck=false,或调整-Xmx/-Xms参数,排查是否是JVM内存管理与内核缓存交互导致的异常。

内容的提问来源于stack exchange,提问作者tom.chen

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.15 15:45:42