第十七章 JAVA I/O 系统
1、File类:
定义了一系列与操作系统无关的方法来操作文件和目录。一个File对象可以代表一个文件,也可以代表一个目录。创建一个File类对象后,如果是目录可以显示目录清单、新建或删除目录;如果是文件,可以查阅文件袋属性和路径信息,也可以输出和改名。可以通过查阅API帮助文档了解更多的相关内容。
2、I/O慨念
在Java编程中,I/O系统主要负责文件的读写,一般在运行程序时,Java I/O 程序将原磁盘、文件或网络上的数据通过输入流类的相应方法读入到内存中,然后通过输出流类的相应方法将处理完的数据写回目标文件、磁盘或网络资源指定位置。I/O系统类库位于java.io包中,提供了全面的I/O接口,包括文件读写、标准设备输出等。Java中I/O是以流为基础进行输入和输出,所有数据被串行化写入输入流,或者从输入流读入。
流的慨念:
流(Stream)是一个抽象的慨念,代表一串数据的集合,当Java程序需要从数据源读取数据时,就需要开启一个数据源的流。同样,当程序需要输出数据到目标的地时,也需要开启一个流。流的创建是为了方便处理数据的输入和输出。
可以把数据流想象成现实生活中的水流,每户人家中要用自来水,就需要再加和自来水厂之间接上一根水管,这样水厂的水才能通过管道留到用户家中。同样,要把河流中的水引导到自来水厂,也需要在河流和水厂之间接上一根水管,这样河流中的水才能流到水厂去。水管就相当于流,而水就是相当于数据源。
在Java程序中,要想获得数据源中的数据,需要在程序和数据源之间建立一个数据输入的通道,这样就能从数据源中获得数据。如果要在程序中把数据写到数据源中,也需要在程序和数据元之间建立一个数据输出通道。在程序中创建输入流对象时就会自动建立这个数据输入通道,而创建输出流对象时就会自动建立这个数据输出通道。
Java程序(读取数据)《======输入流======数据源
Java程序(写出数据)=======输出流======》数据源
3、流的分类:
Java中的流可以按如下方式分类:
1) 按数据流向
输入流:程序可以向其中读取数据源
输出流:程序可以向其中输出数据的流
2) 按数据传输单位
字节流:以字节为单位传输数据的流(主要用于处理可直接读取bytes的数字)
字符流:以字符为单位传输数据的流(主要用于处理文本)
3) 按流的功能
字节流:用于直接操作数据源的流
过滤流:也叫作处理流,是对一个已存在流的链接和封装。来提供更为强大、灵活读写功能。
4、I/O流的使用
抽象类
字节流 字符流
输入流 InputStream Reader
输出流 OutputStream Writer
InputStream和OutputStream都是以字节为单位的抽象流,他们规定了字节流所有输入和输出的基本操作。InputStream和OutputStream抽象类不能直接使用,而是使用子类(具体类)完成不同的功能。
Reader和Writer都是以字符为单位的抽象类。它们规定了所有字符流输入和输出的基本操作。Reader和Writer抽象类不能直接使用。而是使用子类(具体类)完成不同的功能。
5、I/O具体类(实现类)
1)FileInputStream和FileOutputStream:
是以字节为操作单位的文件输入流和文件输出流。利用这两个类可以对文件进行读写操作。
注意:
FileInputStream读取中文字符会出现乱码,原因是在Unicode编码中,一个英文字符是一个字节编码,而一个中文字符则是用两个字节编码,而用字节流读取中文时,是一个一个字节读取,所以会出现编码错误。
FileOutputStream往文件中写入的中文字符没有乱码,原因是程序先把中文字符转成了字节数组,打开文件时文件编辑器(如Windows记事本或其他工具)能自动识别中文字符。
2)FileReader和FileWriter:
是以字符位创作单位的文件输入流和文件输出流。录用这两个类可以对字符文本文件进行读写操作。
注意:FileReader读取中文字符不会出现乱码。
3)BufferInputSteam和BufferOutputSteam:
针对字节的缓冲输入流和输出流。利用这两个累可以提高读取数据读写的速度。因为他们会创建一个内部缓冲区数组,所以读取或写入的字节,都会先填充这个缓冲区,然后一次性读取或写入到目标数据源中。
4)BufferedReader和BufferedWriter:
针对字符的缓冲输入流和输出流。利用这两个累可以提高数据读写的速度。BufferedReader还指出读取整行数据。
注意:
在操作字节文件字符文件时。建议使用带缓冲功能的输入流和输出流,以提高程序的效率。
5)其他输入流和输出流
ZipInputStream和ZipoutputStream:实现ZIP压缩文件的读写功能;
RandomAccessFile:实现在文件的任何地方读写数据;
PrintStream和PrintWriter:实现提供一系列的Print和println方法;
System.out.println中的system.out 就是PrintStream的实例。
DataInputStream和DataOutputStream:实现从文件读取和写入文本的基本类型的数据。
InputstreamReader和OutputStreamWriter:实现字节流和字符流之间的转换。
6、对象的序列化和反序列化
JDK提供了ObjectOututStream和ObjectInputStream两个类用于存储和读取基本数据类型或对象。他最强大之处就是可以把Java中的对象写入到数据源中,也能把对象从数据源中还原回来。
用ObjectOututStream类存储基本类型数据或对象的机制叫做序列化;
用ObjectInputStream类读取基本数据类型数据或对象的机制叫反序列化;
特点:
1) 能被序列化的对象所对应的累必须实现java.io.Serializable这个标示性接口(接口中没有抽象方法)。凡是实现该接口的类都有一个表示序列化版本标识的静态变量。
Private static final langserialVersionUID;//用来表明累的不同版本的兼容性,可以通过Eclipse自动添加。
2) 在序列化过程中,其所属的static属性和方法代码不能被序列化处理。
3) 对于个别不希望被序列化的非static属性,可以在属性声明时使用transient关键字进行标明。