bufferedinputstream是java中基于装饰器模式的字节缓冲输入流,用于增强inputstream子类(如fileinputstream)的读取效率,通过默认8192字节缓冲区减少系统i/o调用次数,适用于二进制数据处理,不支持字符编码解析,不可直接用于文本读取。

BufferedInputStream 是 Java 中用于增强字节流读取性能的装饰器类,它本身属于字节流(InputStream 的子类),**不能直接用于字符流操作**。想用缓冲提高读取效率,需分清场景:处理二进制数据(如图片、音频)用字节流 + BufferedInputStream;处理文本(如中文、英文文件)推荐用字符流 + BufferedReader。
什么时候该用 BufferedInputStream
当你需要高效读取原始字节(比如复制文件、解析二进制协议、读取图片资源),且底层是 InputStream(如 FileInputStream、Socket.getInputStream())时,套一层 BufferedInputStream 能显著减少系统 I/O 调用次数。
- 它内部维护一个字节数组缓冲区(默认 8192 字节),read() 时优先从缓冲区取,不够再触发真实读取
- 适合多次调用
read()、read(byte[])或readLine()(不推荐,易乱码)的场景 - 不要对已缓冲的流(如
BufferedInputStream)再套一层缓冲,无意义
基本用法示例(字节流 + BufferedInputStream)
以下是从文件读取字节并打印前 100 字节的典型写法:
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
<font color="#888">try (FileInputStream fis = new FileInputStream("data.bin");
BufferedInputStream bis = new BufferedInputStream(fis)) {
byte[] buffer = new byte[100];
int len = bis.read(buffer);
System.out.println("读到 " + len + " 字节: " + Arrays.toString(buffer));
}</font>
- 务必使用 try-with-resources 自动关闭,否则缓冲区可能未刷新、流未释放
-
BufferedInputStream不改变底层流的行为,只是加了缓存逻辑 - 若需按行读文本,不要用
bis.readLine()(该方法不存在!InputStream没有 readLine,那是BufferedReader的)
字符流别误用 BufferedInputStream
如果目标是读取 UTF-8 编码的文本文件,直接用 BufferedInputStream 会出问题:
- 它只认字节,不处理字符编码,
read()返回的是 raw byte,中文可能被截断成乱码 - 正确做法是:用
InputStreamReader将字节流解码为字符流,再套BufferedReader
<font color="#888">try (FileInputStream fis = new FileInputStream("text.txt");
InputStreamReader isr = new InputStreamReader(fis, StandardCharsets.UTF_8);
BufferedReader br = new BufferedReader(isr)) {
String line;
while ((line = br.readLine()) != null) {
System.out.println(line);
}
}</font>
小技巧:调整缓冲区大小
默认 8KB 缓冲区适合大多数场景,但若读取超大文件或网络流,可手动指定更大缓冲区提升吞吐:
<font color="#888">BufferedInputStream bis = new BufferedInputStream(fis, 64 * 1024); // 64KB</font>
- 缓冲区不是越大越好,过大会增加内存占用,且对小文件读取反而可能变慢
- 一般 8KB–64KB 是较稳妥范围,具体根据数据源特征和 JVM 堆配置权衡
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










