Java IO流是Java中处理输入输出的核心机制,通过不同的流类型实现了对数据的高效读写。
一、IO流的分类
1. 按数据方向
- 输入流(Input Stream):从数据源(如文件、网络等)读取数据。
- 输出流(Output Stream):向目标(如文件、网络等)写入数据。
2. 按数据类型
- 字节流(Byte Streams):以字节(8位)为单位操作,处理所有二进制数据(如图片、音频、视频等)。
- 基类:InputStream 和 OutputStream。
- 字符流(Character Streams):以字符(16位Unicode)为单位操作,专门处理文本数据。
- 基类:Reader 和 Writer。
3. 按功能
- 节点流(Node Streams):直接操作数据源(如文件流)。
- 处理流(Processing Streams):对现有流进行包装,增强功能(如缓冲、转换格式)。
二、核心类与常用流
1. 字节流
- InputStream(输入流)
- FileInputStream:从文件读取字节。
- ByteArrayInputStream:从字节数组读取。
- BufferedInputStream:提供缓冲功能,减少IO次数。
- DataInputStream:读取Java基本数据类型(如int、double)。
- ObjectInputStream:反序列化对象(需实现Serializable接口)。
- OutputStream(输出流)
- FileOutputStream:向文件写入字节。
- ByteArrayOutputStream:写入字节数组。
- BufferedOutputStream:缓冲输出流。
- DataOutputStream:写入Java基本数据类型。
- ObjectOutputStream:序列化对象。
2. 字符流
- Reader(字符输入流)
- FileReader:读取文本文件。
- BufferedReader:提供缓冲功能,支持readLine()逐行读取。
- InputStreamReader:将字节流转换为字符流(可指定编码)。
- Writer(字符输出流)
- FileWriter:写入文本文件。
- BufferedWriter:缓冲输出流。
- OutputStreamWriter:将字符流转换为字节流(可指定编码)。
3. 转换流
- InputStreamReader 和 OutputStreamWriter:用于字节流与字符流的转换,支持字符编码(如UTF-8、GBK)。
三、示例代码
1. 文件读写
- 字节流示例(复制文件):
try (FileInputStream fis = new FileInputStream("input.jpg"); FileOutputStream fos = new FileOutputStream("output.jpg")) { byte[] buffer = new byte[1024]; int bytesRead; while ((bytesRead = fis.read(buffer)) != -1) { fos.write(buffer, 0, bytesRead); } }
- 字符流示例(逐行读取文本):
try (BufferedReader br = new BufferedReader(new FileReader("file.txt"))) { String line; while ((line = br.readLine()) != null) { System.out.println(line); } }
2. 对象序列化
// 序列化
try (ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream("data.obj"))) {
oos.writeObject(new Person("Alice", 30));
}
// 反序列化
try (ObjectInputStream ois = new ObjectInputStream(new FileInputStream("data.obj"))) {
Person p = (Person) ois.readObject();
}
3. 缓冲流提升性能
// 使用缓冲流复制文件(效率更高)
try (BufferedInputStream bis = new BufferedInputStream(new FileInputStream("input.txt"));
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("output.txt"))) {
int data;
while ((data = bis.read()) != -1) {
bos.write(data);
}
}
四、IO流的使用场景
IO流主要用于处理输入和输出操作,适用于以下场景:
- 文件读写:通过IO流可以读取和写入文件中的数据,如读取配置文件、写入日志等。
- 网络通信:通过IO流可以进行网络数据的传输和接收,如Socket通信、HTTP请求等。
- 数据库操作:通过IO流可以将数据读取到内存中,或将内存中的数据写入到数据库中。
- 文本处理:通过IO流可以读取和写入文本文件,进行文本处理和操作。
五、高级特性
- NIO(New I/O)
- Java 1.4引入的java.nio包,提供非阻塞IO、通道(Channel)、缓冲区(Buffer)等机制,适合高并发场景。
- 核心类:ByteBuffer, FileChannel, Selector。
- 自动资源管理(try-with-resources)
- Java 7+支持自动关闭实现了AutoCloseable接口的资源:
try (Resource1 r1 = new Resource1(); Resource2 r2 = new Resource2()) { // 使用资源 } // 自动调用close()
- Java 7+支持自动关闭实现了AutoCloseable接口的资源:
六、常见问题
- 字节流 vs 字符流
- 字节流处理二进制数据,字符流处理文本(自动处理编码)。
- 文本文件建议用字符流,避免编码问题。
- 选择缓冲流
- 频繁读写时,缓冲流通过减少IO次数提升性能。
- 字符编码问题
- 使用InputStreamReader/OutputStreamWriter时需指定编码(如UTF-8)。
七、总结
Java IO流通过分层设计(节点流+处理流)和装饰器模式,灵活支持多种数据操作场景。掌握字节流、字符流及缓冲机制是高效处理IO的关键,同时注意资源释放和编码问题。对于高性能需求,可进一步学习NIO框架。