缓冲流的概述,使用过基本的字节流完成文件的复制,并统计用了多长时间
字节缓冲流
字节输入缓冲流 BufferedInputStream
字节输出缓冲流 BufferedOutputStream
字符缓冲流
字符输入缓冲流BufferedReader
字符输出缓冲流 BufferedWriter
缓冲流的特点效率高,使用缓冲流可以提高读写的效率,原因是缓冲流内部有一个缓冲区,他可以提高效率
缓冲流本身并不具备读或者写的功能,他的功能是给其他流提供加速
字节缓冲流的构造方法
BufferedInputStream(InputStream in) 参数要传递一个字节输入流
BufferedOutputStream(OutputStream out) 参数要传递字节输出流
字节缓冲流读写的方法
字节缓冲流属于字节流,里面读写的方法和字节流读写的方法一模一样
字符缓冲流
字符缓冲流的使用步骤
创建字符缓冲流对象,调用方法读或者写 ,释放资源
注意 如果字符输出流,那么写完需要刷新
字符缓冲流中有一些特有的方法
BufferedWriter中有一个特有的方法
void newLine() 向文件中写一个换行符,这个换行符是跨平台的
BufferedReader中的特有方法
String readLine() 读取一行数据,并将读取到的这行数据返回,如果已经读取结束了,返回null 该方法不会读取换行符
转换流
字符编码
计算机中储存的信息都是用二进制数标书的,我们在屏幕上看到的数组,英文,标点符号,汉子等字符都是二进制数转换之后的结果,按照某种规则,将字符存储
编码 字符转字节 解码 字节转字符
比如按照一定的规则才可以进行编码 解码
编码表(字符集)是字节和字符的对应关系表
ASCII 是最先出现的一个编码表,上面的字符都是占一个字节 可以保存128个英文,数组,以及常见的标点符号
ISO8859-1 占一个字节 包含256个字符,除了支持英文之外,还支持拉丁文
GB2312 1/2字节 包含了六千多个汉字以及符号
big5 1/2字节 支持繁体字
GBK 1/2字节 包含了两万多个汉字以及符号
Unicode国际标准码表,可以保存所有国家的语言在unicode中每一个字符都是用两个字节存储的 unicode8.0的时候,甚至还可以支持emoji
基于unicode,出现utf-8
utf-32 每一个字符都是4个字节的
utf-16 每一个字符都是占2/3/4个字节的
utf-8 每一个字符都是占1/2/3/4字节的
只需要记住GBK和UTF-8
在window操作系统的默认编码是GBK
在GBK编码中一个中文占2个字节
在UTF-8编码中一个中文占3个字节
英文在这个两个编码表中都是占一个字节的
使用FileReader读取文件中的数据
在文件中aa.txt采用的是GBK编码,但是FileReader会采用ider开发工具的编码去读取,idea采用的默认编码是UTF-8此时两种编码不一致,就会导致乱码问题
如果解决 需要用指定的编码去读,需要用转换流
转换流的特点 可以指定编码读取数据
InputStreamReader 是转换流,用来读取,可以指定编码读取数据
InputStreamReader 是一个字符流,可以以字符为单位进行读取
InputStreamReader构造方法
InputStreamReader(InputStream in)参数要传递一个字节输入流,该构造方法创建的对象会读取idea默认的编码进行读取
InputStreamReader(InputStream in,String charsetName)第一个参数要传递字节输入流,第二个参数要传递字符串的编码方式
这个转换流的作用是输入
InputStreamReader的读取方法
InputStreamReader属于字符流,里面读取的方法和字符流一模一样
InputStreamReader的使用步骤
创建一个转换流对象,指定编码,用来读取,调用read方法读取数据,释放资源
windows会自动识别文件的编码 自己新建的他不会
OuputStreamWriter 是转换流,用来写,可以指定编码写数据
OuputStreamWriter 是属于字符流,会以字符为单位写数据
OuputStreamWriter的构造方法
OuputStreamWriter(OutputStream out)参数要传递一个字节输出流,该构造方法创建的转换流对象会使用idea默认编码去写数据
OuputStreamWriter(OutoutSream out ,String charsetName)第一个参数要传递字节输出流,第二个参数要传递编码方式,会以指定编码写数据
OuputStreamWriter的使用步骤
创建OuputStreamWriter转换流对象,用来写,并指定编码
调用writer方法写数据
刷新
释放资源
因为OuputStreamWriter属于字符输入流的一种,所以写完要刷新
序列化流
将java程序中的对象写到文件中,如果要进行序列化操作可以使用序列化流
ObjectOutoutStream是序列化流,可以将java程序中的对象写到文件中
ObjectOutoutStream的构造方法
ObjectOutoutStream(OuputStream out)参数要传递一个字节输出流
ObjectOutoutStream的特有方法
void writeObject(Object obj)将对象写到文件中,参数要写入的是JAVA类对象
ObjectOutoutStream的使用步骤
创建序列化流对象,用来写
调用writerObject方法,写对象
释放资源
注意要序列化的对象,一定要实现serializable接口
这个接口没有任何方法,这个接口只是起到一个标记作用,实现这个接口才可以将该类的对象写到文件中
ObjectInputStream 是反序列化流,可以将文件中的对象读取到java程序中
ObjectInputStream的构造方法
ObjectInputStream构造方法
ObjectInputStream(InputStream in)参数要传递一个字节输入流对象
ObjectInputStreaam读取对象的方法(特有方法)
Object readObject() 从文件中读取对象
ObjectInputStream使用步骤
创建ObjectInputStream反序列化流对象
调用readObject方法读取
释放资源
注意 如果读取对象的时候,对象所对应的类不存在,那么会抛出ClassNotFoundException异常
注意 static修饰的成员变量不能被序列化,为什么?因为static修饰的成员是属于类的,不属于对象,而序列化写的是对象
如果不想某个成员变量被序列化,同时又不希望使用static关键字,那么可以使用transient,transient表示瞬态,被transient修饰的成员变量不能被序列化,除此之外没有其他作用
对实体类进行编译,会生成实体类.class,在编译的时候会给这个类生成一个版本号(序列号),保存在class文件中
使用序列化流将实体类对象写到文件中,实体类中的版本号也会一起写到文件中。
如果使用ObjectInputStream反序列化流读取对象,那么会对比当前类中的版本号和文件中保存的版本号是否一致,如果不一致那么就会报错,如果想要解决版本号不一致的问题,那么可以给类固定一个版本号,固定版本号之后,不管类怎么修改,版本号都不变
如何给类固定一个版本号
可以在类中提供一个成员变量(真正是一个常量)这个成员固定用private static final修饰并且是long类型的,这个成员变量叫做serivlVersionUID 不管类如何修改,版本号永远都是你设置的值
打印流
PintSream是打印流,打印流有以下特点
打印流只有输出流,没有输入流
写数据十分的方便,他是属于字节流的一部分
pintStream构造方法
pintStream(File file)参数要传递一个File类型的文件
printStream(OutputStream out)参数要传递一个字节输出流
printStream(String fileName)参数要传递一个字符串的文件路径
printStream写数据的方法(特有方法)
void print(任何类型)写任何类型的数据
void println(任何类型)写任何类型的数据并换行
之前使用的的System.out.println就是一个打印流,这个打印流叫做标准输入流,该输入流的目的地是控制台
可以使用System.中的静态方法setOut来改变标准输出流的方向
参数要传递一个打印流,传递的打印流绑定的目的地是什么,将来使用System.out.println的位置就是打印流绑定的位置