字符流
前面学习的字节流和字符流都是基本流,其中字符流的底层其实已经在内存中创建了一个长度为8192的字节数组作为缓存区。而字节流中则是没有的。
在内存中增加缓冲区的目的是为了减少内存与硬盘的交互的次数,因为这一操作比较耗时。
下面是一个图示例:
缓冲区是什么时候创建的呢?
答案是在创建流的时候创建的。
字符输入流读取数据
当首次使用read方法从硬盘中读取文件时会先一次性地读取8192个字节到缓冲区中,后面再读取时会从缓冲区中读取。当缓冲区中的数据读完时会再次到文件中读,文件中的数据也读完时会返回-1。
字符输出流写入数据
当使用write方法向文件中写入数据时并不是直接就写到文件中,而是先写到缓冲区中,当缓冲区满时再一次性地写到文件中。或者不满时也想写到文件中时可以使用flush方法,当关闭输出流时也会将缓冲区中的数据写到文件中。
缓冲流
于是又设计出来一些高级流,比如字节缓冲流和字符缓冲流。
(1)缓冲流在使用时要传递基本流的对象过去,因为缓冲流只是对基本流包装了一下,并增加了缓冲区,但是干活的其实还是基本流。
(2)其实缓冲流就是在底层增加了一个长度为8192的数组作为缓冲区。
字节缓冲流的缓冲区是byte类型的,而字符缓冲流的缓冲区则是char类型的数组。
所以字节缓冲流的缓冲区大小是8192B=8*1024B=8KB,字符缓冲流的缓冲区的大小为8192*2B=16KB。
字节缓冲流
如何创建它们的对象呢?
2个构造方法,可以看到需要传递字节流的对象过去。
方法名 | 说明 |
---|---|
public BufferedInputStream(InputStream in) | 创建一个缓冲输入流 |
public BufferedOutputStream(OutputStream out) | 创建一个缓冲输出流 |
细节:
只用关闭字节缓存流,字节流的对象是不用管的,因为字节缓存流会帮我们关闭。
字符缓冲流
字符缓冲流由于字节流中本来就有缓存区,因此效率提升不大,但是有2个特有方法。
细节1:readLine()会读取换行符之前的数据并进行返回。
细节2:newLine()方法,当想写入换行符时,不同的系统中换行符是不一样的,比如Mac是\r,Linux中则是\n,Windows中则是\r\n。代码中直接写换行符其实是不合理的,比如同一个代码,放到不同的系统中效果是不一样的,这样不好,于是就要newLine()方法, 不同的系统中效果都是一样的。