IO流
IO流
概述
IO:Input(输入),Output(输出),往一个文件中输出内容或从一个文件中读取内容,这个过程就是IO操作。
输入Input:读取外部数据(磁盘,光盘等存储设备的数据)到程序(内存)中。
输出Ouput:将程序(内存)数据输出到磁盘,光盘等存储设备中。
IO分类
Java.io包下提供了各种“流”类和接口,用以获取不同种类的数据,并通过标准的方法输入或输出数据。
①按照数据的流向不同分为:输入流和输出流(从内存角度上看)
输入流:把数据从其它设备上读取内存中的流
输出流:把数据从内存中写到其它设备上的流
②按操作数据单位的不同分为:字节流(8bit)和字符流(16bit)
字节流:以字节为单位,读写数据的流
字符流:以字符为单位,读写数据的流
③根据IO流的角色不同分为:节点流和处理流
节点流:直接从数据源或目的地读写数据
处理流:不直接连接到数据源或目的地,而是“连接”在已存在的流(节点流或处理流)之上,通过对数据的处理为程序提供更为强大的读写功能
IO流框架
本章中主要学习标注红色的流。
InputStream类
它是一个字节输入流,流的内容是字节单位,它是所有直接输入流的父类。而该类中最常用的一个子类FileInputStream。这种流适合图片,音频,视频的操作。
操作步骤:
第1步:创建读取的File类的对象
第2步:创建FileInputStream输入流
第3步:具体的读入的过程
read():一个一个进行读取,当没有字符时返回-1
第4步:关闭流资源,避免内存泄露
举个例子:
1 public class Test {
2 public static void main(String[] args) {
3 FileInputStream fs= null;
4 try {
5 //1.创建file文件对象
6 File file =new File("a.txt");
7 //2.创建输入流(这里会存在异常需要进行处理)
8 fs = new FileInputStream(file);
9 int a;
10 //3.读取一个一个字符,当文件没有内容时会返回-1
11 //这里的read()方法会有异常需要进行处理
12 while((a=fs.read())!=-1){
13 System.out.println((char)a);
14 }
15 } catch (IOException e) {
16 System.out.print(e.getMessage());
17 } finally {
18 //4.关闭资源
19 try {
20 //这里需要判断如果有FileInputStream时才需要关闭资源
21 if(fs!=null){
22 fs.close();
23 }
24 } catch (IOException e) {
25 System.out.println(e.getMessage());
26 }
27 }
28 }
29 }
效果展示:
OutputStream类
字节输出流,往文件中写入的内容为字节。OutputStream是字节输出流的父类,它也是一个抽象类,FileOutputStream是它的实现类。
操作步骤:
第1步:创建写出的File类的对象
第2步:创建FileOutputStream输出流(如果文件不存在时会创建文件)
第3步:具体的写出的过程
write(int b):将指定的字节写到指定文件
write(byte[] s):将指定的字节写到指定文件
第4步:关闭资源
举个例子:
1 public class Test{
2 public static void main(String[] args) {
3 //1.创建文件对象
4 File file = new File("b.txt");
5 //2.创建FileOutStream对象
6 FileOutputStream os = null;
7 try {
8 //创建OutputStream流对象--如果指定的文件不存在则创建。
9 os = new FileOutputStream(file,true);
10 //3.调用FileOutStream类中的方法完成输出操作
11 String msg="你好 今天学习IO流";
12 os.write(msg.getBytes());
13 } catch (Exception e) {
14 e.printStackTrace();
15 } finally {
16 //4.关闭流资源
17 if (os != null) {
18 try {
19 os.close();
20 } catch (IOException e) {
21 e.printStackTrace();
22 }
23 }
24 }
25 }
26 }
效果展示:
当文件不存在的时候,会自动创建指定的文件。
该类用于读取的内容为字符类型,它是所有字符输入流的父类,它比较适合读取文本内容,它常用的子类FileReader类
操作步骤:
第1步:创建读取的File类的对象
第2步:创建FileReader输入流
第3步:具体的读入的过程
read():一个一个进行读取,当没有字符时返回-1
第4步:关闭流资源,避免内存泄露
举个例子:
1 public class Test {
2 public static void main(String[] args) {
3 Reader reader=null;
4 try{
5 //创建一个输入字符流对象
6 reader=new FileReader(new File("b.txt"));
7 //调用Reader类中方法完成读取功能
8 int c = -1;
9 while ((c=reader.read())!=-1){
10 System.out.print((char)c);
11 }
12 }catch (Exception e){
13 e.printStackTrace();
14 }finally {
15 //关闭资源
16 if(reader!=null){
17 try {
18 reader.close();
19 } catch (IOException e) {
20 e.printStackTrace();
21 }
22 }
23 }
24 }
25 }
效果展示:
该类用于读取的内容为字符类型,它是所有字符输出流的父类,它比较适合读取文本内容,它常用的子类FileWriter类
第1步:创建写出的File类的对象 第2步:创建FileWriter输出流 第3步:具体的写出的过程
write(int b):将指定的字节写到指定文件
write(byte[] s):将指定的字节写到指定文件
第4步:关闭流资源,避免内存泄露
举个例子:
1 public class Test {
2 public static void main(String[] args) {
3 Writer writer = null;
4 try {
5 //1.创建一个字符输出流对象--
6 writer=new FileWriter(new File("c.txt"));
7 //2.调用里面的输出方法
8 String msg="今天是个好日志,心想的事儿都能成.";
9 writer.write(msg);
10 } catch (Exception e) {
11 e.printStackTrace();
12 } finally {
13 if (writer != null) {
14 try {
15 writer.close();
16 } catch (IOException e) {
17 e.printStackTrace();
18 }
19 }
20 }
21 }
22 }
效果展示:
为什么说字节流更适合操作图片,音频,视频操作,而字符流更适合操作文件呢
>对于字符流只能用来操作文本文件,不能用来处理非文本
>对于字节流,通常用来处理非文本的,因为当处理文本时如果里面内容存在中文会出现乱码,所以更适合操作图片,音频,视频操作。
说明:
文本文件:.txt、.java、.c、.cpp、.py等
非文本文件:.doc、.xls、.jpg、.pdf、.mp3、.avi等
缓冲流
BufferedInputStream-----缓冲字节输入流
BufferedOutputStream-----缓冲字节输出流
BufferedReader----------缓冲字符输入流
BufferedWriter------------缓冲字符输出流
BufferedInputStream类
缓冲字节输入流,用于FileInputStream输入流
操作步骤:
第1步:创建读取的File类对象
第2步:创建FileInputStream输入流
第3步:创建BufferedInputStream缓冲字节输入流
第4步:具体的读取的过程
read():一个一个进行读取,如果后面没有内容返回-1
readLine():整行读取,但是不换行
第5步:关闭缓冲流资源,避免内存泄露
举个例子:
1 public class Test {
2 public static void main(String[] args) {
3 BufferedInputStream bis= null;
4 try {
5 //创建一个FileInputStream对象
6 InputStream is=new FileInputStream(new File("a.txt"));
7 //创建一个BufferedInputStream对象
8 bis = new BufferedInputStream(is);
9 //调用BufferedInputStream的方法
10 int c;
11 while((c=bis.read())!=-1){
12 System.out.print((char)c);
13 }
14 } catch (IOException e) {
15 e.printStackTrace();
16 } finally {
17 //关闭缓冲流资源
18 if(bis!=null){
19 try {
20 bis.close();
21 } catch (IOException e) {
22 e.printStackTrace();
23 }
24 }
25 }
26 }
27 }
效果展示:
BufferedOutputStream类
缓冲字节输出流,用于FileOutputStream输出流
操作步骤:
第1步:创建写出的File类对象
第2步:创建FileOutputStream输出流对象
第3步:创建BufferedOutputStream缓冲字节输出流
第4步:具体的写出的过程
write(byte[] b):将指定的字节写到指定文件
write(int b):将指定的字节写到指定文件
第5步:关闭流资源,避免内存泄露
举个例子:
1 public class Test {
2 public static void main(String[] args) {
3 BufferedOutputStream bis= null;
4 try {
5 //创建FileIn
6 FileOutputStream is=new FileOutputStream(new File("a.txt"));
7
8 //创建一个BufferedOutputStream对象
9 bis = new BufferedOutputStream(is);
10 //调用BufferedOutputStream的方法
11 byte[] arr={12,97,20,34};
12 bis.write(arr);
13
14 } catch (IOException e) {
15 e.printStackTrace();
16 } finally {
17 if(bis!=null){
18 try {
19 bis.close();
20 } catch (IOException e) {
21 e.printStackTrace();
22 }
23 }
24 }
25 }
26 }
效果展示:
BufferedReader类
缓冲字节输入流,用于FileReader输入流
操作步骤:
第1步:创建读入的File类的对象
第2步:创建FileReader输入流对象
第3步:创建BufferedReader缓冲输入流对象
第4步:具体的读入的过程
int read():一个一个字符读取,直到没有字符返回-1
String readLine():一行一行字符读取,不换行,直到没有字符返回null
第5步:关闭缓冲流,避免内存泄露
举个例子:
1 public class Test {
2 public static void main(String[] args) {
3 FileReader fr = null;
4 BufferedReader br = null;
5 try {
6 fr = new FileReader(new File("c.txt"));
7 br = new BufferedReader(fr);
8 String ch;
9 while ((ch = br.readLine()) != null) {
10 System.out.println(ch);
11
12 }
13 } catch (IOException e) {
14 e.printStackTrace();
15 } finally {
16 if(br!=null){
17 try {
18 br.close();
19 } catch (IOException e) {
20 e.printStackTrace();
21 }
22 }
23 if(fr!=null){
24
25 try {
26 fr.close();
27 } catch (IOException e) {
28 e.printStackTrace();
29 }
30 }
31 }
32 }
33 }
效果展示:
BufferedWriter类
缓冲字节输出流,用于FileReader输出流
操作步骤:
第1步:创建读入的File类的对象
第2步:创建FileWriter输入流对象
第3步:创建BufferedWriter缓冲输入流对象
第4步:具体的读入的过程
void write(String c):写入一个字符串
void newLine():写一行分隔符
第5步:关闭缓冲流,避免内存泄露
举个例子:
1 public class Test {
2 public static void main(String[] args) {
3 FileWriter fw = null;
4 BufferedWriter bw = null;
5 try {
6 fw = new FileWriter(new File("b.txt"));
7 bw = new BufferedWriter(fw);
8 String str = "今天天气真好!";
9 bw.write(str);
10 bw.newLine();
11 } catch (IOException e) {
12 e.printStackTrace();
13 } finally {
14 if (bw != null) {
15
16 try {
17 bw.close();
18 } catch (IOException e) {
19 e.printStackTrace();
20 }
21 }
22 if (fw != null) {
23
24 try {
25 fw.close();
26 } catch (IOException e) {
27 e.printStackTrace();
28 }
29 }
30 }
31
32 }
33 }
效果展示:
对象流
对象流概述
对象流用于操作java对象,可以把java对象从内存保存到文件中,也可以把文件中对象读取到内存中。
序列化:通过对象流把内存中的对象保存磁盘 | 网络上这个过程-------------------称为序列化
反序列化:通过对象流把磁盘 | 网络上的对象转化为内存中的对象这个过程---------------称为反序列化
处理流分为两种:
第一种:ObjectInputStream: 对象输入流
第二种:ObjectOutputStream: 对象输出流
对象输出流
通过对象流把内存中的对象保存磁盘 | 网络上这个过程
操作步骤:
第1步:创建对象
第2步:创建存放磁盘的位置
第3步:将对象存储到文件中
writeObject(对象):将对象存放到磁盘中
第4步:关闭对象流资源
举个例子:
1 public class Test {
2 public static void main(String[] args) {
3 FileOutputStream fs= null;
4 ObjectOutputStream ois= null;
5 try {
6 //1.创建对象
7 Student s1=new Student("张三",13);
8 //2.存放在磁盘中的位置
9 File file=new File("a.txt");
10 fs = new FileOutputStream(file);
11 ois = new ObjectOutputStream(fs);
12 //3.将对象存储到文件中
13 ois.writeObject(s1);
14 } catch (IOException e) {
15 e.printStackTrace();
16 } finally {
17 if(ois!=null){
18 try {
19 ois.close();
20 } catch (IOException e) {
21 e.printStackTrace();
22 }
23 }
24 if(fs!=null){
25 try {
26 fs.close();
27 } catch (IOException e) {
28 e.printStackTrace();
29 }
30 }
31 }
32 }
33 }
效果展示:
发现会报错,这是因为对象没有实现序列化Serializable接口,所以会出现异常。
解决方法:(只需要在类上实现Serializable接口即可)
1 class Student implements Serializable{
2 private String name;
3 private int age;
4
5 public Student() {
6 }
7
8 public Student(String name, int age) {
9 this.name = name;
10 this.age = age;
11 }
12 public String getName() {
13 return name;
14 }
15 public void setName(String name) {
16 this.name = name;
17 }
18 public int getAge() {
19 return age;
20 }
21 public void setAge(int age) {
22 this.age = age;
23 }
24
25 public String toString() {
26 return "Student{name = " + name + ", age = " + age + "}";
27 }
28 }
效果展示:
在文件中加载成功,注意这不是给你看的是给计算机看的。
对象输入流
通过对象流把磁盘 | 网络上的对象转化为内存中的对象这个过程-
操作步骤:
第1步:创建之前存放对象的文件
第2步:创建对象输入流
第3步:使用对象输入流获取对象
readObject():获取对象
第4步:关闭流资源
举个例子:
1 public class Test {
2 public static void main(String[] args) {
3
4 ObjectInputStream ois= null;
5 try {
6 //1.创建之前存放对象的文件
7 File file=new File("a.txt");
8 //2.创建对象输入流
9 ois = new ObjectInputStream(new FileInputStream(file));
10 //3.由于反序列化时不知道文件中的对象是什么类型
11 //所以我们可以使用向下转型的方式
12 Student student =(Student)ois.readObject();
13 System.out.println(student);
14 } catch (IOException e) {
15 e.printStackTrace();
16 } catch (ClassNotFoundException e) {
17 e.printStackTrace();
18 } finally {
19 //4.关闭流资源
20 if(ois!=null){
21
22 try {
23 ois.close();
24 } catch (IOException e) {
25 e.printStackTrace();
26 }
27 }
28 }
29
30 }
31 }
效果展示: