1. 概述
本文将介绍如何将 File
对象转换为 InputStream
——分别使用 原生 Java、Guava 和 Apache Commons IO 三种方式实现。
这类操作在文件处理、IO 转换中非常常见,属于基础但高频的“踩坑点”。掌握多种写法,能让你在不同项目环境下游刃有余。
本文是 Baeldung 系列教程 《Java – 回归基础》 的一部分。
2. 使用原生 Java 转换
Java 自带的 java.io
包提供了多种将文件转为输入流的方式。以下是几种典型用法。
2.1. FileInputStream
最直接、最常用的方式就是 FileInputStream
,简单粗暴,适合大多数场景。
✅ 适用于单个文件读取,性能好,无需额外依赖。
@Test
public void givenUsingPlainJava_whenConvertingFileToInputStream_thenCorrect()
throws IOException {
File initialFile = new File("src/main/resources/sample.txt");
InputStream targetStream = new FileInputStream(initialFile);
}
⚠️ 注意:该流需手动关闭(或使用 try-with-resources),否则可能引发资源泄漏。
2.2. DataInputStream
如果你需要从文件中读取二进制数据或基本类型(如 int、double、boolean),可以结合 DataInputStream
使用。
它本身不是文件流,而是装饰器模式的应用,必须包装另一个 InputStream
。
@Test
public final void givenUsingPlainJava_whenConvertingFileToDataInputStream_thenCorrect()
throws IOException {
final File initialFile = new File("src/test/resources/sample.txt");
final InputStream targetStream =
new DataInputStream(new FileInputStream(initialFile));
}
✅ 适合处理 .dat
等二进制格式文件
❌ 不适用于普通文本读取(建议用 BufferedReader
)
2.3. SequenceInputStream
当你想把多个文件的内容合并成一个逻辑流时,SequenceInputStream
就派上用场了。
它可以把两个 InputStream
串联起来,按顺序读取。
@Test
public final void givenUsingPlainJava_whenConvertingFileToSequenceInputStream_thenCorrect()
throws IOException {
final File initialFile = new File("src/test/resources/sample.txt");
final File anotherFile = new File("src/test/resources/anothersample.txt");
final InputStream targetStream = new FileInputStream(initialFile);
final InputStream anotherTargetStream = new FileInputStream(anotherFile);
InputStream sequenceTargetStream =
new SequenceInputStream(targetStream, anotherTargetStream);
}
✅ 实现文件内容拼接而无需实际合并文件
⚠️ 注意:两个流的关闭行为需特别处理——关闭 SequenceInputStream
会自动关闭内部的两个流
⚠️ 示例中省略了流的关闭逻辑,仅为代码清晰。生产环境务必使用 try-with-resources 或显式关闭。
3. 使用 Guava 转换
Google Guava 提供了更优雅的 IO 操作封装。通过 Files.asByteSource()
可以轻松获得文件的字节源,再打开流。
✅ 代码简洁,API 设计友好
✅ 在使用 Guava 的项目中推荐使用
@Test
public void givenUsingGuava_whenConvertingFileToInputStream_thenCorrect()
throws IOException {
File initialFile = new File("src/main/resources/sample.txt");
InputStream targetStream = Files.asByteSource(initialFile).openStream();
}
💡 提示:ByteSource
是 Guava 的核心抽象之一,支持缓存、哈希、复制等高级操作,适合复杂场景。
4. 使用 Apache Commons IO 转换
Apache Commons IO 是 Java 开发者的“老朋友”,FileUtils.openInputStream()
方法简洁明了。
✅ 社区广泛使用,稳定性高
✅ 自动处理一些边界情况(如文件不存在抛 IOException
)
@Test
public void givenUsingCommonsIO_whenConvertingFileToInputStream_thenCorrect()
throws IOException {
File initialFile = new File("src/main/resources/sample.txt");
InputStream targetStream = FileUtils.openInputStream(initialFile);
}
⚠️ 需引入依赖:
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>2.11.0</version>
</dependency>
5. 总结
方式 | 是否需要依赖 | 特点 |
---|---|---|
✅ FileInputStream |
否 | 原生支持,最基础 |
✅ DataInputStream |
否 | 用于读取二进制/基本类型 |
✅ SequenceInputStream |
否 | 合并多个文件流 |
✅ Guava Files.asByteSource() |
是 | API 优雅,功能丰富 |
✅ Commons IO FileUtils.openInputStream() |
是 | 简洁稳定,广泛使用 |
📌 选择建议:
- 项目无依赖 ➜ 用
FileInputStream
- 已引入 Guava ➜ 优先用
Files.asByteSource().openStream()
- 已引入 Commons IO ➜ 直接调
FileUtils.openInputStream()
所有示例代码均可在 GitHub 获取:https://github.com/eugenp/tutorials/tree/master/core-java-modules/core-java-io-conversions
这是一个基于 Maven 的项目,导入即可运行,适合本地验证和学习。