Java复习,Java知识点以及Java面试题(七)

IO流

  用来处理设备之间的数据传输

  IO流的分类:按流向:输入流(读取数据);输出流(写出数据)

        按数据类型:字节流:

                字节输入流  读取数据 InputStream

                字节输出流  写出数据  OutputStream

              字符流:为了方便操作文本数据

                字符输入流 读取数据 Reader

                字符输出流 写出数据 Writer

   InputStream,OutputStream,Reader,Writer都是抽象类,不能实例化,所以我们要使用具体的子类。每种基类的子类都是以父类名作为后缀名:

  XxxOutputStream,XxxInputStream,XxxReader,XxxWriter

  FileOutputStream:

    构造方法:FileOutputStream(File file)

            FileOutputStream(String name)

            FileOutputStream(String name;Boolean ture)

    成员方法:public void wirte(int b):

         public void wirte(byte[] b):

         public void wirte(byte[] b, int off, int len)

    字节输出流操作步骤:创建字节输出流-->写数据-->释放资源,关闭此文件输出流并释放与此流有关的所有系统资源(.close() )

    创建字节输出流对象做了几件事情:

      A. 调用系统功能去创建文件

      B. 创建FileOutputStream对象

      C. 把对象指向这个文件

    为什么一定要close()呢?

      A. 让流对象变成垃圾,这样就可以被垃圾回收器回收了

      B. 通知系统去释放跟该文件相关的资源

    实现数据换行

      加换行符号:

        Windos:\r\n; linux:\n; Mac: \r;

    如何实现追加写入数据:

      使用构造方法:FileOutputStream(String name;Boolean ture)

    写入数据时的异常处理:

 1         // 为了在finally里面能够看到该对象就必须定义到外面,为了访问不出问题,还必须给初始化值
 2         FileOutputStream fos = null;
 3         try {
 4             // fos = new FileOutputStream("z:\\fos4.txt");
 5             fos = new FileOutputStream("fos4.txt");
 6             fos.write("java".getBytes());
 7         } catch (FileNotFoundException e) {
 8             e.printStackTrace();
 9         } catch (IOException e) {
10             e.printStackTrace();
11         } finally {
12             // 如果fos不是null,才需要close()
13             if (fos != null) {
14                 // 为了保证close()一定会执行,就放到这里了
15                 try {
16                     fos.close();
17                 } catch (IOException e) {
18                     e.printStackTrace();
19                 }
20             }
21         }

    FileInputStream

      字节输入流操作步骤:创建字节输入流对象-->调用read()方法读取数据,并把数据显示在控制台-->释放资源

    构造方法同FileOutputStream

    成员方法:public int read(): 一次读取一个字节

         public int read(byte[] b): 一次读取一个字节数组 返回值是实际读取的字节个数。如果到末尾就返回-1

    计算机时如何识别什么时候该把两个字节转换为一个中文呢?

      在计算机中中文的存储分两个字节:第一个字节肯定是负数,第二个字节常见是负数,可能是正数。但是没有影响。

    

    通过定义数组的方式确实比以前一次读取一个字节的方式快很多,所以,缓冲区非常有用,java就在开始设计的时候,提供了带缓冲区的字节类。这种类被称为:缓冲区类(高效类)。写数据:BufferedOutputStream;读数据:BufferedInputStream

    构造方法可以指定缓冲区的大小,但是我们一般用不上,因为默认缓冲区大小足够了。

    为什么不传递一个具体的文件或者文件路径,而是传递一个OutputStream对象呢?因为字节缓冲区流仅仅提供缓冲区,为高效而设计的,但是真正的读写操作还得靠基本的流对象实现.

 

  字符流 = 字节流 + 编码表(由现实世界的字符和对应的数值组成的一张表)

     

  String类中的编码和解码问题:

    String(byte[] bytes, String charsetName): 通过指定的字符集解码字节数组

    byte[] getBytes(String charsetName):使用指定的字符集合把字符串编码为字节数组

  

  OutputStreamWrite

    OutputStreamWriter(OutputStream out): 根据默认编码把字节流的数据转换为字符流

    OutputStreamWriter(OutputStream out, String charsetName):根据指定编码把字节流数据转换为字符流

    字符流的五种写数据的方法:

      public void write(int c):写一个字符

      public void write(char[] cbuf):写一个字符数组

      public void write(char[] cbuf,int off,int len):写一个字符数组的一部分

      public void write(String str):写一个字符串

      public void write(String str,int off,int len):写一个字符串的一部分

    close()和flush()的区别?

      A:close()关闭流对象,但是先刷新一次缓冲区。关闭之后,流对象不可以继续再使用了(即不能书写和读取数据,否则报错)。

      B:  仅仅刷新缓冲区,刷新之后,流对象还可以继续使用。

  InputStreamReader

    InputStreamReader(InputStream is): 用默认的编码读取数据

    InputStreamReader(InputStream is, String charsetName): 根据指定的编码读取数据

    字符流读数据的两种方法:

        public int read():一次读取一个字符

        public int read(char[] chs):一次读取一个字符数组

 

  由于我们常见的操作都是使用本地默认编码,所以,不用指定编码。

  而转换流的名称有点长,所以,Java就提供了其子类供我们使用FileWriter,FileReader

    

  字符缓冲流

    字符流为了高效读写,也提供了对应的字符缓冲流

    BufferedWriter:字符缓冲输出流:将文本写入字符输出流,缓冲各个字符,从而提供的单个字符,数组和字符串的高效写入。可以指定缓冲区的大小,或者可使用默认的大小。大多数情况下,默认值就足够大了

    BufferedReader:字符缓冲输入流:从字符输入流中读取文本,缓冲各个字符,从而提供的单个字符,数组和字符串的高效写入。可以指定缓冲区的大小,或者可使用默认的大小。大多数情况下,默认值就足够大了

    特殊方法:

      BufferedWriter: public void newLine(): 根据系统来决定换行符

      BufferdReader:public String readLine(): 一次读取一个一行数据

  

  

 

 

  1 import java.io.BufferedReader;
  2 import java.io.BufferedWriter;
  3 import java.io.FileReader;
  4 import java.io.FileWriter;
  5 import java.io.IOException;
  6 
  7 /*
  8  * 复制文本文件
  9  * 
 10  * 分析:
 11  *         复制数据,如果我们知道用记事本打开并能够读懂,就用字符流,否则用字节流。
 12  *         通过该原理,我们知道我们应该采用字符流更方便一些。
 13  *         而字符流有5种方式,所以做这个题目我们有5种方式。推荐掌握第5种。
 14  * 数据源:
 15  *         c:\\a.txt -- FileReader -- BufferdReader
 16  * 目的地:
 17  *         d:\\b.txt -- FileWriter -- BufferedWriter
 18  */
 19 public class CopyFileDemo {
 20     public static void main(String[] args) throws IOException {
 21         String srcString = "c:\\a.txt";
 22         String destString = "d:\\b.txt";
 23         // method1(srcString, destString);
 24         // method2(srcString, destString);
 25         // method3(srcString, destString);
 26         // method4(srcString, destString);
 27         method5(srcString, destString);
 28     }
 29 
 30     // 字符缓冲流一次读写一个字符串
 31     private static void method5(String srcString, String destString)
 32             throws IOException {
 33         BufferedReader br = new BufferedReader(new FileReader(srcString));
 34         BufferedWriter bw = new BufferedWriter(new FileWriter(destString));
 35 
 36         String line = null;
 37         while ((line = br.readLine()) != null) {
 38             bw.write(line);
 39             bw.newLine();
 40             bw.flush();
 41         }
 42 
 43         bw.close();
 44         br.close();
 45     }
 46 
 47     // 字符缓冲流一次读写一个字符数组
 48     private static void method4(String srcString, String destString)
 49             throws IOException {
 50         BufferedReader br = new BufferedReader(new FileReader(srcString));
 51         BufferedWriter bw = new BufferedWriter(new FileWriter(destString));
 52 
 53         char[] chs = new char[1024];
 54         int len = 0;
 55         while ((len = br.read(chs)) != -1) {
 56             bw.write(chs, 0, len);
 57         }
 58 
 59         bw.close();
 60         br.close();
 61     }
 62 
 63     // 字符缓冲流一次读写一个字符
 64     private static void method3(String srcString, String destString)
 65             throws IOException {
 66         BufferedReader br = new BufferedReader(new FileReader(srcString));
 67         BufferedWriter bw = new BufferedWriter(new FileWriter(destString));
 68 
 69         int ch = 0;
 70         while ((ch = br.read()) != -1) {
 71             bw.write(ch);
 72         }
 73 
 74         bw.close();
 75         br.close();
 76     }
 77 
 78     // 基本字符流一次读写一个字符数组
 79     private static void method2(String srcString, String destString)
 80             throws IOException {
 81         FileReader fr = new FileReader(srcString);
 82         FileWriter fw = new FileWriter(destString);
 83 
 84         char[] chs = new char[1024];
 85         int len = 0;
 86         while ((len = fr.read(chs)) != -1) {
 87             fw.write(chs, 0, len);
 88         }
 89 
 90         fw.close();
 91         fr.close();
 92     }
 93 
 94     // 基本字符流一次读写一个字符
 95     private static void method1(String srcString, String destString)
 96             throws IOException {
 97         FileReader fr = new FileReader(srcString);
 98         FileWriter fw = new FileWriter(destString);
 99 
100         int ch = 0;
101         while ((ch = fr.read()) != -1) {
102             fw.write(ch);
103         }
104 
105         fw.close();
106         fr.close();
107     }
108 }

 

 

 1 import java.io.BufferedInputStream;
 2 import java.io.BufferedOutputStream;
 3 import java.io.File;
 4 import java.io.FileInputStream;
 5 import java.io.FileOutputStream;
 6 import java.io.IOException;
 7 
 8 /*
 9  * 复制图片
10  * 
11  * 分析:
12  *         复制数据,如果我们知道用记事本打开并能够读懂,就用字符流,否则用字节流。
13  *         通过该原理,我们知道我们应该采用字节流。
14  *         而字节流有4种方式,所以做这个题目我们有4种方式。推荐掌握第4种。
15  * 
16  * 数据源:
17  *         c:\\a.jpg -- FileInputStream -- BufferedInputStream
18  * 目的地:
19  *         d:\\b.jpg -- FileOutputStream -- BufferedOutputStream
20  */
21 public class CopyImageDemo {
22     public static void main(String[] args) throws IOException {
23         // 使用字符串作为路径
24         // String srcString = "c:\\a.jpg";
25         // String destString = "d:\\b.jpg";
26         // 使用File对象做为参数
27         File srcFile = new File("c:\\a.jpg");
28         File destFile = new File("d:\\b.jpg");
29 
30         // method1(srcFile, destFile);
31         // method2(srcFile, destFile);
32         // method3(srcFile, destFile);
33         method4(srcFile, destFile);
34     }
35 
36     // 字节缓冲流一次读写一个字节数组
37     private static void method4(File srcFile, File destFile) throws IOException {
38         BufferedInputStream bis = new BufferedInputStream(new FileInputStream(
39                 srcFile));
40         BufferedOutputStream bos = new BufferedOutputStream(
41                 new FileOutputStream(destFile));
42 
43         byte[] bys = new byte[1024];
44         int len = 0;
45         while ((len = bis.read(bys)) != -1) {
46             bos.write(bys, 0, len);
47         }
48 
49         bos.close();
50         bis.close();
51     }
52 
53     // 字节缓冲流一次读写一个字节
54     private static void method3(File srcFile, File destFile) throws IOException {
55         BufferedInputStream bis = new BufferedInputStream(new FileInputStream(
56                 srcFile));
57         BufferedOutputStream bos = new BufferedOutputStream(
58                 new FileOutputStream(destFile));
59 
60         int by = 0;
61         while ((by = bis.read()) != -1) {
62             bos.write(by);
63         }
64 
65         bos.close();
66         bis.close();
67     }
68 
69     // 基本字节流一次读写一个字节数组
70     private static void method2(File srcFile, File destFile) throws IOException {
71         FileInputStream fis = new FileInputStream(srcFile);
72         FileOutputStream fos = new FileOutputStream(destFile);
73 
74         byte[] bys = new byte[1024];
75         int len = 0;
76         while ((len = fis.read(bys)) != -1) {
77             fos.write(bys, 0, len);
78         }
79 
80         fos.close();
81         fis.close();
82     }
83 
84     // 基本字节流一次读写一个字节
85     private static void method1(File srcFile, File destFile) throws IOException {
86         FileInputStream fis = new FileInputStream(srcFile);
87         FileOutputStream fos = new FileOutputStream(destFile);
88 
89         int by = 0;
90         while ((by = fis.read()) != -1) {
91             fos.write(by);
92         }
93 
94         fos.close();
95         fis.close();
96     }
97 }

 

操作基本数据类型的流

   可以读写基本类型的数据

   数据输入流:DataInputStream

      DataInputStream(InputStream in)   

   数据输出流: DataOutputStream

       DataOutputStream(OutputStream out)

内存操作流: 用于处理临时存储信息的,程序结束,数据就从内存中消失

  操作字节数组

    ByteArrayInputStream

    ByteArrayOutputStream

  操作字符数组

    CharArrayReader

    CharArrayWriter

  操作字符串

    StringReader

    StringWriter

打印流

  字节打印流 PrintStream

  字符打印流 PrintWriter

  只有写数据的,没有读数据的,只能操作目的地,不能操作数据源

  可以操作任意类型的数据

    print()  println()

  如果启动了自动刷新,能够自动刷新

    PrintWriter pw = new PrintWriter(new FileWriter("pw2.txt"),ture);

    还是应该调用println()的方法才可以

    这个时候不仅仅自动刷新了,还实现了数据的换行

  该流是可以直接操作文本文件的

    哪些流对象是可以直接操作文本文件的呢?

      FileInputStream  FileOutputStream

      FileReader           FileWriter

      PrintStream    PrintWriter

      看API,查流对象的构造方法,如果同时有File类型和String类型的参数,一般来说就是可以直接操作文件的

      基本流:能够直接读写文件的

      高级流:在基本流的基础上提供了一些其他的功能

标准输入输出流 

  System类中的两个成员变量:

    public static final InputStream in “标准”输入流。

    public static final PrintStream out “标准”输出流。

 

    InputStream is = System.in;

    PrintStream ps = System.out;

随机访问流

   不属于流,是Object类的子类,但它融合了InputStream和OutputStream的功能,支持对文件的随机访问读取和写入。

  public RandomAccessFile(String name, String mode): 第一个参数是文件路径,第二个参数是操作文件的模式。模式一般常用‘rw’,既可以写数据也可以读数据

 

posted @ 2020-10-15 23:21  生于思考  阅读(88)  评论(0编辑  收藏  举报