bufferedreader 按换行符( 、 或 )分割行,readline() 返回不带换行符的字符串,末尾无换行符时返回 null。

Java 中 BufferedReader 本身只按换行符(
、、<code>
)分隔行,不支持多分隔符(如 ||、##、\t 等)的“按行”语义读取。所谓“自定义多分隔符按行读取”,本质是**绕过默认换行逻辑,手动缓冲 + 按指定分隔符切分内容流**。
用 StringBuilder 手动缓冲 + 自定义分隔符查找
核心思路:不依赖 readLine(),改用 read(char[]) 或 read() 逐批读入字符,拼到 StringBuilder 中,然后在缓冲区里查找任意一个你定义的分隔符(如 "||"、"##"、" "),截取并返回“逻辑行”。
- 定义分隔符集合(如
List<string> delimiters = Arrays.asList("||", "##", " ")</string>) - 每次读入一批字符追加到
buffer(StringBuilder) - 扫描
buffer,找最先出现的任意分隔符位置(注意要按最长匹配优先,避免"|"和"||"冲突) - 若找到,截取从开头到该分隔符前的内容作为一行,更新
buffer剩余部分;否则继续读 - 支持流式处理,内存可控,适合大文件
预处理为单一分隔符再用标准 readLine
如果源数据量不大、或允许一次加载,可先将所有自定义分隔符统一替换成标准换行符(如
),再用普通 BufferedReader 读取。简单直接,但不适用于超大流式场景。
- 例如:
content.replaceAll("(\|\||##|\t)", " ") - 注意转义:正则中
|、需正确表达("\|\||##|\t") - 替换后构造新
StringReader或写入临时ByteArrayInputStream - 适合配置文件、小批量日志等场景
封装成 Iterable 或 Stream 接口提升复用性
把上述逻辑封装成一个可迭代对象,让调用方像用 for (String line : customReader) 一样使用,更符合 Java 习惯。
- 实现
Iterator<string></string>,内部维护BufferedReader和缓冲区 - 重写
hasNext()和next(),延迟解析每行 - 可进一步提供
lines()方法返回Stream<string></string> - 避免一次性加载全部内容,保持流式友好
注意边界与编码细节
实际使用时容易忽略几个关键点:
- 分隔符跨 buffer 边界:比如
"||"被拆在两次read()中(前次末尾是"|",下次开头是"|"),需保留末尾少量字符用于回溯匹配 - 编码一致性:确保
BufferedReader构造时指定正确字符集(如new InputStreamReader(in, StandardCharsets.UTF_8)) - 空行和结尾无分隔符:最后一段内容没被分隔符截断,需在
close()或hasNext()结束时主动返回剩余内容 - 性能权衡:频繁
indexOf多个分隔符可用 Aho-Corasick 算法优化,但一般场景用循环查找已足够
不复杂但容易忽略细节。关键是明确“按行”在这里是业务定义,不是系统换行,所以得自己掌控切分逻辑。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











