IO流

本文最后更新于:1 年前

IO流

什么是IO

I/O输入/输出(Input/Output),分为IO设备和IO接口两个部分。 在POSIX兼容的系统上,例如Linux系统 [1] ,I/O操作可以有多种方式,比如DIO(Direct I/O),AIO(Asynchronous I/O,异步I/O),Memory-Mapped I/O(内存映射I/O)等,不同的I/O方式有不同的实现方式和性能,在不同的应用中可以按情况选择不同的I/O方式。

百度百科

我们把数据的传输看为数据的流动,按照流动的方向,以内存为基准,分为输入input和输出output即流向内存是输入流,流出内存是输出流。

IO的分类

根据数据的流向分为

  • 输入流:把数据从其他设备读取到内存中
  • 输出流:把数据从内存中写入到其他设备

根据数据类型分为

  • 字节流:以字节为单位,读写数据的流
  • 字符流:以字符为单位,读写数据的流

顶级父类们

输入流 输出流
字节流 字节输入流InputStream 字节输出流OutputStream
字符流 字符输入流Reader 字符输出流Writer

字节流

一切皆为字节

一切数据都是以二进制数字的形式保存的,都是一个个的字节。字节流可以传输任何数据

字节输出流

写出字节数据

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
package io;

import java.io.FileOutputStream;
import java.io.IOException;

/*
java.io.OutputStream 字节输出流
此抽象类是表示输出字节流的所有类的超类。输出流接受输出字节并将这些字节发送到某个接收器。

成员方法
void close() 关闭此输出流并释放与此流有关的所有系统资源。
void flush() 刷新此输出流并强制写出所有缓冲的输出字节。
void write(byte[] b) 将 b.length个字节从指定的 byte 数组写入此输出流。
void write(byte[] b, int off, int len) 将指定 byte 数组中从偏移量 off 开始的 len 个字节写入此输出流。
abstract void write(int b) 将指定的字节写入此输出流。

java.io.FileOutputStream extends OutputStream
FileOutputStream 文件输出流
构造方法
FileOutputStream(String name) 创建一个向具有指定名称的文件中写入数据的输出文件流。
FileOutputStream(File file) 创建一个向指定 File 对象表示的文件中写入数据的文件输出流。
...
构造方法的作用:
创建一个FileOutputStream对象
根据构造方法中传递的文件路径、文件名,创造一个空的文件
把FileOutputStream对象指向该文件
写入数据的原理:
Java程序-->JVM-->OS-->OS中的写入数据方法-->将数据写入文件
字节输出流的使用
1.创建一个FileOutputStream对象,构造方法中传入写入数据的目的地
2.调用FileOutputStream对象中的write方法,把数据写入到文件
3.释放资源(凡是涉及到IO流的使用的都会占用一定的内存资源,使用完毕一定要记得关闭,节省系统资源,提升程序效率)

*/
public class IODemo01 {
public static void main(String[] args) throws IOException {
//1.创建一个FileOutputStream对象,构造方法中传入写入数据的目的地
FileOutputStream fos = new FileOutputStream("C:\\Users\\MaLin\\Desktop\\JavaCode\\src\\io\\a.txt");
//2.调用FileOutputStream对象中的write方法,把数据写入到文件
fos.write(97);
//3.释放资源(凡是涉及到IO流的使用的都会占用一定的内存资源,使用完毕一定要记得关闭,节省系统资源,提升程序效率)
fos.close();
}
}

文件存储原理

文本编辑器读取文件原理

在任意文本编辑器中,打开文件都会查询编码表、

0-127 查询ASCII码表

​ 97–a

​ ···

其他 查询当前系统默认码表,中文系统GBK码表

一次写多个字节的方法

  • public void write(byte[] b):将b.length字节从指定的字节数组写入此输出流
  • public void write(byte[] b, int off, int length):从指定的字节数组写入length个字节,从偏移量off开始输出到此输出流
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
package io;

import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.util.Arrays;

public class OutputStream {
public static void main(String[] args) throws IOException {
FileOutputStream fos1 = new FileOutputStream("b.txt");
fos1.write(49);
fos1.write(48);
fos1.write(48);

/*
public void write(byte[] b):将b.length字节从指定的字节数组写入此输出流
一次写多个字节
如果第一个字节是正数(0-127)那么就会查询ASCII码表
如果第一个字节是负数,那么第一个字节和第二个字节会组成一个中文显示,查询系统默认码表(GBK简体中文)

*/
byte[] bytes = {65, 66, 67 ,68};

fos1.write(bytes);
fos1.write(bytes, 1, 2);
/*
写入字符的方法,String类有个方法可以把字符串转换为字节数组
byte[] getBytes()
*/
byte[] bytes1 = "你好".getBytes();
System.out.println(Arrays.toString(bytes1));//[-28, -67, -96, -27, -91, -67] utf-8编码
fos1.write(bytes1);

fos1.close();
}
}

数据追加续写

  • public FileOutoutStream(File file, boolean append):创建文件输出流以写入有指定File对象表示的文件
  • public FileOutputStream(String name, boolean append):创建文件输出流以写入指定名称的文件
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
package io;

import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.charset.StandardCharsets;

/*
FileOutputStream(String name, boolean append)
创建一个向具有指定 name 的文件中写入数据的输出文件流。
FileOutputStream(File file, boolean append)
创建一个向指定 File 对象表示的文件中写入数据的文件输出流。
*/
public class OutputStreamDemo02 {
public static void main(String[] args) throws IOException {
FileOutputStream fileOutputStream = new FileOutputStream("1.txt", true);
for (int i = 0; i < 10; i++) {
fileOutputStream.write("你好".getBytes(StandardCharsets.UTF_8));
fileOutputStream.write("\r\n".getBytes(StandardCharsets.UTF_8));
}
fileOutputStream.write("你好".getBytes(StandardCharsets.UTF_8));
fileOutputStream.close();

}
}

1
2
3
4
5
6
7
8
9
10
11
你好
你好
你好
你好
你好
你好
你好
你好
你好
你好
你好

字节输入流


博主码字不易,本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!