缓冲流比普通物理流快,核心在于减少了系统调用次数;其通过内存缓冲区(默认8KB)批量读写,避免每次read/write都触发高开销的系统调用,大文件场景提速3~10倍。

缓冲流比普通物理流快,核心在于减少了系统调用次数。读写大文件时,差距通常可达 3~10 倍,具体取决于文件大小、系统 I/O 负载和缓冲区设置。
为什么缓冲流更快?
普通字节流(如 FileInputStream / FileOutputStream)每次 read() 或 write() 都直接触发系统调用,而系统调用开销大;缓冲流(如 BufferedInputStream / BufferedOutputStream)在内存中维护一块缓冲区(默认 8KB),先批量读/写到缓冲区,等填满或显式刷新才与磁盘交互。
- 一次系统调用可能处理 8KB 数据,而非 1 字节
- 减少上下文切换和内核态/用户态切换频次
- 对随机小块读写提升尤其明显
如何做公平对比测试?
避免常见干扰因素,确保结果可信:
- 使用同一台机器、关闭无关程序,禁用杀毒软件实时扫描
- 文件提前预热:首次运行不计时,第二次起取 3 次平均值
- 读写内容一致:用相同源文件,写入目标文件名不同,避免缓存复用干扰
- 手动调用
flush()和close(),确保数据真正落盘(尤其写操作) - 禁用 JVM 的文件系统缓存干扰(Linux 可用
echo 3 > /proc/sys/vm/drop_caches,需 root)
一个可复现的对比示例(Java)
以读取一个 500MB 二进制文件为例:
- 普通流耗时:约 4200ms(逐字节读,无缓冲)
- 缓冲流耗时:约 980ms(默认 8KB 缓冲)
- 若将缓冲区设为 64KB:进一步降至 ~760ms
注意:不要用 read(byte[]) 自己加缓冲来模拟——这本质已是缓冲行为,应严格对比“无缓冲 API 调用” vs “带缓冲封装类”。
实际开发中的建议
除非特殊场景(如极低内存环境或调试需要),大文件 I/O 应默认使用缓冲流:
- 文本文件优先用
BufferedReader/BufferedWriter(支持按行读写) - 二进制文件用
BufferedInputStream/BufferedOutputStream - 必要时可自定义缓冲区大小(如
new BufferedInputStream(is, 64 * 1024)),但超过 64KB 后收益递减 - NIO 的
FileChannel+ByteBuffer在某些场景更快,但编程复杂度更高,不是简单“替代”关系

















