首页 > 代码库 > java中文件的读与写

java中文件的读与写

 最近一直在学习java中如何读取和写出文件,看了java API之后,发现在java.io中有很多关于文件读与写的类,下面就介绍几个经常用到的.

 首先是:InputStream和OutputStream,API中说它俩是所有抽象类表示字节输入输出流的超类,所以在它们下面派生了很多子类.例如:FileInputStream和OutputStream等等.这些类都是以单字节的形式读入数据的,所以如果读入的数据中有中文字符,那么就会出现中文乱码现象.

 其次是:Reader和Writer,这两个类是用于读取字符的(一个字符是两个字节).这两个类和上面的两个类称之为节点流.节点流的含义可以直接从或向一个特定的地方(节点)读写数据.下面以InputStream和Reader读入数据为例:

 1 package com.file;
 2 
 3 import java.io.File;
 4 import java.io.FileInputStream;
 5 import java.io.FileNotFoundException;
 6 import java.io.FileReader;
 7 import java.io.IOException;
 8 import java.io.InputStream;
 9 import java.io.Reader;
10 
11 public class readFileDirect {
12     
13     //InputStream类读取文件是依靠字节的方式,所以读取中文必定会出现乱码(一个中文字符是两个字节)
14     public static void readFileByInputStream(String filePath){
15         File file = new File(filePath);
16         int b = 0;
17         try {
18             InputStream is = new FileInputStream(file);
19             
20             try {
21                 while((b=is.read())!=-1){
22                     System.out.print((char)b);
23                 }
24                 is.close();
25                 System.out.println("文件读取结束");
26             } catch (IOException e) {
27                 System.out.println("读取文件失败");
28                 e.printStackTrace();
29                 System.exit(-1);
30             }
31         } catch (FileNotFoundException e) {
32             System.out.println("文件未找到");
33             e.printStackTrace();
34             System.exit(-1);
35         }
36     }
37     
38     //Reader类读取文件依靠字符的方式,所以读取文件不会出现乱码
39     public static void readFilesByReader(String filePath){
40         File files = new File(filePath);
41         
42         try {
43             Reader in = new FileReader(files);
44             int c = 0;
45             
46             try {
47                 while((c=in.read())!=-1){
48                     if(in.ready()){
49                         System.out.print((char)c);
50                     }
51                 }
52                 
53                 in.close();
54             } catch (IOException e) {
55                 System.out.println("文件读取错误");
56                 e.printStackTrace();
57                 System.exit(-1);
58             }
59             
60         } catch (FileNotFoundException e) {
61             System.out.println("没有找到指定文件");
62             e.printStackTrace();
63             System.exit(-1);
64         }
65     }
66     
67     public static void main(String[] args) {
68         readFileByInputStream(System.getProperty("user.dir")+"/src/com/file/readFileDirect.java");
69         readFilesByReader(System.getProperty("user.dir")+"/src/com/file/readFileDirect.java");
70     }
71 }

 执行main函数后,会发现readFileByInputStream方法读入的数据中中文会乱码,而readFilesByReader方法却不会.

 与节点流不同的是处理流,所谓处理流,我的理解是:在节点流读入或者写出数据的过程中,对其编码方式,读取方式等进行某些处理,使之读取或者写入文件的方式更加好.用到的处理流是在java.io中的BufferedInputStream和BufferedOutputStream,BufferedReader和BuffereWriter.从类名就可以看出,前者是针对实现了InputStream和OutputStream的子类做处理,而后者是针对实现了Reader和Writer的子类进行处理.下面是我对这两个类的使用,还是以BufferedInputStream和BufferedReader为例:

 1 package com.file;
 2 
 3 import java.io.BufferedInputStream;
 4 import java.io.BufferedReader;
 5 import java.io.File;
 6 import java.io.FileInputStream;
 7 import java.io.FileNotFoundException;
 8 import java.io.FileReader;
 9 import java.io.IOException;
10 import java.io.Reader;
11 
12 public class readFileInDirect {
13     
14     //使用BufferedReader对流进行处理
15     public static void readFileByBufferedReader(String filePath){
16         File file = new File(filePath);
17         
18         if(file.exists()&&file.isFile()){    //判断文件是否存在
19             String lineTxt = null;
20             try {
21                 Reader is = new FileReader(file);
22                 BufferedReader bis = new BufferedReader(is);
23                 
24                 try {
25                     while((lineTxt=bis.readLine())!=null){    //读取文件的一整行.
26                         if(bis.ready()){    //判断是否阻塞.
27                             System.out.println(lineTxt);
28                         }
29                     }
30                 } catch (IOException e) {
31                     System.out.println("文件读取错误");
32                     e.printStackTrace();
33                     System.exit(-1);
34                 }
35                 
36             } catch (FileNotFoundException e) {
37                 System.out.println("未找到指定的文件");
38                 e.printStackTrace();
39                 System.exit(-1);
40             }
41         }else{
42             System.out.println("文件已经存在");
43             System.exit(-1);
44         }
45     }
46     
47     
48     //使用BufferedInputStream对流进行处理
49     
50     public static void readFileByBufferedInputStream(String filePath){
51         File files = new File(filePath);
52         
53         if(files.isFile()&&files.exists()){
54             try {
55                 int line = 0;
56                 
57                 BufferedInputStream bis = new BufferedInputStream(new FileInputStream(files));
58                 try {
59                     while((line=bis.read())!=-1){
60                         
61                         System.out.print((char)line);
62                     }
63                 } catch (IOException e) {
64                     System.out.println("读取文件失败");
65                     e.printStackTrace();
66                     System.exit(-1);
67                 }
68             } catch (FileNotFoundException e) {
69                 System.out.println("找不到指定的文件");
70                 e.printStackTrace();
71                 System.exit(-1);
72             }
73         }
74     }
75     
76     public static void main(String[] args) {
77         readFileByBufferedReader(System.getProperty("user.dir")+"/src/com/file/readFileInDirect.java");
78         readFileByBufferedInputStream(System.getProperty("user.dir")+"/src/com/file/readFileInDirect.java");
79     }
80 }

 执行main函数之后会发现第一个方法能够完整的读入文件,而第二个方法却出现了乱码,这是正常的,因为即使使用了BufferedInputStream,它读取文件的方式还是以单字节读取,所以遇到中文字符(两个字节)还是会乱码.

 当然如果你读取文件的时候还想从字节转向字符,并且指定读取或者写出的编码方式,这时就需要InputStreamReader和OutputStreamWriter.具体代码就不给出了.多看看API就会使用的.方法类似上面.