IO流用来处理设备之间的数据传输,java对数据的操作是通过流的方式,java用于操作的流对象都在IO包中,流按照操作的数据,分为两种,字节流和字符流
IO流的常用基类:
字节流的抽象基类:InputStream,OutputStream
字符流的抽象基类:Reader,Writer
由这四个类派生出来的子类的名称都是以其父类名作为其子类名的后缀
FileWriter:
1: class FileWriterDemo
2: {
3: public static void main(String[] args) throws IOException
4: {
5: //创建一个FileWriter对象,该对象一被初始化就必须要有明确的被操作的文件,
6: //而且该文件会被创建到指定的目录下去,如果该目录下已经有同名的文件,则会覆盖原来的文件。
7: FileWriter fw=new FileWriter("demo.txt");
8:
9: //使用FileWriter对象的write方法,将数据写入到输入输出流中去
10: fw.write("abcde");
11:
12: //刷新流对象的缓冲中的数据,将数据流刷新到目标文件中去,刷新后依旧可以继续往目标文件中存数据
13: fw.flush();
14:
15: //关闭数据流,关闭之前会先进行刷新,关闭以后不可以继续往目标文件中存数据
16: fw.close();
17:
18:
19:
20: }
21: }
22:
IO异常的处理:
1: class FileWriterDemo
2: {
3: public static void main(String[] args)
4: {
5: //如果在try中创建FileWriter对象,在finally中关闭资源时,会找不到fw。
6: //因此应该在try外面就进行对象的创建。
7: FileWriter fw=null;
8: try
9: {
10: //创建一个FileWriter对象,该对象一被初始化就必须要有明确的被操作的文件,
11: //而且该文件会被创建到指定的目录下去,如果该目录下已经有同名的文件,则会覆盖原来的文件。
12: fw=new FileWriter("demo.txt");
13:
14: //使用FileWriter对象的write方法,将数据写入到输入输出流中去
15: fw.write("abcde");
16:
17: //刷新流对象的缓冲中的数据,将数据流刷新到目标文件中去,刷新后依旧可以继续往目标文件中存数据
18: fw.flush();
19:
20: }
21: catch (IOException e)
22: {
23: throw new RuntimeException("写入数据发生错误");
24: }
25: finally
26: {
27: try
28: {
29: //如果没有对fw进行初始化,则full为null,因此,fw并不具备close功能
30: //如果进行关闭,会捕获到NullPointerException
31: if(fw!=null)
32: //关闭数据流,关闭之前会先进行刷新,关闭以后不可以继续往目标文件中存数据
33: fw.close();
34: }
35: catch (IOException e)
36: {
37: throw new RuntimeException("关闭资源失败");
38: }
39:
40: }
41:
42: }
43: }
44:
文件的续写:
1: class FileWriterDemo
2: {
3: public static void main(String[] args)
4: {
5: //如果在try中创建FileWriter对象,在finally中关闭资源时,会找不到fw。
6: //因此应该在try外面就进行对象的创建。
7: FileWriter fw=null;
8: try
9: {
10: //创建一个FileWriter对象,该对象一被初始化就必须要有明确的被操作的文件,
11: //而且该文件会被创建到指定的目录下去
12: //传递一个true参数,表示不覆盖已有的文件,并在已有文件的末尾处进行数据的续写
13: fw=new FileWriter("demo.txt",true);
14:
15: //使用FileWriter对象的write方法,将数据写入到输入输出流中去
16: //在Linux中,\n代表换行,在window内不识别,window内,\r\n代表换行
17: fw.write("nihao\r\nxiexie");
18:
19: //刷新流对象的缓冲中的数据,将数据流刷新到目标文件中去,刷新后依旧可以继续往目标文件中存数据
20: fw.flush();
21:
22: }
23: catch (IOException e)
24: {
25: throw new RuntimeException("写入数据发生错误");
26: }
27: finally
28: {
29: try
30: {
31: //如果没有对fw进行初始化,则full为null,因此,fw并不具备close功能
32: //如果进行关闭,会捕获到NullPointerException
33: if(fw!=null)
34: //关闭数据流,关闭之前会先进行刷新,关闭以后不可以继续往目标文件中存数据
35: fw.close();
36: }
37: catch (IOException e)
38: {
39: throw new RuntimeException("关闭资源失败");
40: }
41:
42: }
43:
44: }
45: }
46:
FileReader:
1: import java.io.*;
2:
3: class FileReaderDemo
4: {
5: public static void main(String[] args) throws IOException
6: {
7: //创建一个文件读取流对象,和指定名称的文件相关联
8: //要保证指定的文件是存在的,如果该文件不存在,会发生FileNotFoundException
9: FileReader fr=new FileReader("demo.txt");
10:
11: //调用读取流对象的read方法,其返回值为int类型
12: //单个字符读取
13: while(true)
14: {
15: int ch=fr.read();
16: if((ch==-1)
17: break;
18: System.out.println("ch="+(char)ch);
19: }
20:
21: //通过数组来读取,将字符读入数组,返回读取的字符数,如果到达了文件的末尾,返回-1
22: //首先应该先定义一个字符数组,用于存储读到的字符
23: char[] buf=new char[1024];
24: int num=0;
25: while((num=fr.read(buf))!=-1)
26: {
27: System.out.println(new String(buf,0,num));
28: }
29:
30: fr.close();
31: }
32: }
33:
拷贝文件:(将C盘下的一个文本文件复制到D盘)
1: import java.io.*;
2:
3: /*
4: 步骤:
5: <1>在D盘下创建一个文件,用来存储从C盘文件中读取到的数据
6: <2>定义一个读取流和C盘文件关联
7: <3>通过不断的读写完成数据的存储
8: <4>关闭资源
9: */
10: class CopyTest
11: {
12: public static void main(String[] args) throws IOException
13: {
14: copy_2();
15:
16: System.out.println("Hello World!");
17: }
18: //一个字符一个字符的复制文件。
19: public static void copy_1()throws IOException
20: {
21: FileWriter fw=new FileWriter("demo2.txt");
22:
23: FileReader fr=new FileReader("c:\\demo.txt");
24:
25: int ch=0;
26: while((ch=fr.read())!=-1)
27: {
28:
29: fw.write((char)ch);
30: }
31:
32:
33: fw.close();
34: fr.close();
35: }
36: //通过数组来复制文件
37:
38: public static void copy_2() throws IOException
39: {
40: FileWriter fw=new FileWriter("FileReaderTest.txt");
41:
42: FileReader fr=new FileReader("c:\\FileReaderTest.java");
43:
44: char[] buf=new char[1024];
45: int num=0;
46:
47: while((num=fr.read(buf))!=-1)
48: {
49: fw.write(buf,0,num);
50: }
51:
52: fw.close();
53: fr.close();
54: }
55:
56: }
57:
BufferedWriter:
缓冲区的出现,是为了提高流的操作效率,所以在创建缓冲区之前,必须先有流对象。
1: import java.io.*;
2:
3:
4: class BufferedWriterDemo
5: {
6: public static void main(String[] args) throws Exception
7: {
8: //创建一个写入流对象,往文件中写入数据
9: FileWriter fw=new FileWriter("buf.txt");
10:
11: //为了提高写入流的效率,加入了缓冲区技术
12: //只要将需要被提高效率的流对象作为参数传递给BufferedWriter的构造函数即可
13:
14: BufferedWriter bufw=new BufferedWriter(fw);
15:
16: bufw.write("abac");
17: //使用到了缓冲区,需要进行刷新,将缓冲区里面的数据刷新到文件中去
18: bufw.flush();
19: //关闭bufw,其实就是关闭缓冲区中的流对象,因此不需要fw.close();
20:
21: bufw.close();
22:
23: }
24: }
25:
BufferedReader:
1: import java.io.*;
2:
3:
4: class BufferedReaderDemo
5: {
6: public static void main(String[] args) throws IOException
7: {
8: FileReader fr=new FileReader("buf.txt");
9: BufferedReader bufr=new BufferedReader(fr);
10:
11: String line=null;
12: //readLine方法的返回值只包含该行的内容,不包含任何的行终止符
13: while((line=bufr.readLine())!=null)
14: {
15: System.out.println(line);
16: }
17:
18: bufr.close();
19:
20: }
21: }
22:
练习:通过缓冲区,复制一个.java文件
1: import java.io.*;
2:
3: class CopyDemo
4: {
5: public static void main(String[] args)
6: {
7: BufferedReader bufr=null;
8: BufferedWriter bufw=null;
9:
10: try
11: {
12: //创建一个读取流对象,用来读取需要被复制的文件
13: bufr=new BufferedReader(new FileReader("BufferedWriterDemo.java"));
14:
15: //创建一个输出流对象,用来将读取到的数据写入到目的文件中去
16: bufw=new BufferedWriter(new FileWriter("BufferedWriterDemo.txt"));
17:
18: String line=null;
19:
20: //读取一行数据,就往新的文件中写入一行数据
21: while((line=bufr.readLine())!=null)
22: {
23: bufw.write(line);
24: bufw.newLine();//换行
25: bufw.flush();//刷新
26: }
27: }
28: catch (IOException e )
29: {
30: throw new RuntimeException("复制文件出现错误");
31: }
32: finally
33: {
34: try
35: {
36: if(bufr!=null)
37: bufr.close();
38: }
39: catch (IOException e)
40: {
41: throw new RuntimeException("关闭读取流失败");
42: }
43:
44: try
45: {
46: if(bufw!=null)
47: bufw.close();
48: }
49: catch (IOException e)
50: {
51: throw new RuntimeException("关闭输出流失败");
52:
53: }
54: }
55: }
56: }
57:
模拟readLine方法:
无论是读取一行数据,但是读取多个字符,在硬盘上都是一个一个的读取,所以最终使用的还是read方法。。
readLine方法,读取单个字符后将字符暂存在一个数组中,当读到\r\n时,将之前的内容一并读取出来
1: import java.io.*;
2: class MyBufferedReader
3: {
4: private FileReader r;
5: MyBufferedReader(FileReader r)
6: {
7: this.r=r;
8: }
9:
10: public String myReadLine()throws IOException
11: {
12: //定义一个临时的容器,用来存放读取到的数据,原BufferedReader中封装的是一个数组
13: //为了方便,定义一个StringBuilder容器,来存放数据
14: StringBuilder sb=new StringBuilder();
15: int ch=0;
16: while((ch=r.read())!=-1)
17: {
18: //如果读取到的字符为\r,则继续读,判断下一个字符是否为\n
19: if(ch==‘\r‘)
20: continue;
21: //如果为\n,说明已经读取了一整行的数据,将存储的一行数据都打印出来,否则继续存入sb中去
22: if(ch==‘\n‘)
23: return sb.toString();
24: else
25: sb.append((char)ch);
26: }
27:
28: //若最后一行数据输完以后,并未输入换行符,那么最后一行数据会丢失
29: //通过判断sb的长度,来判断是否还有数据并未打印,如果有的话,则打印出来
30: if (sb.length()!=0)
31: return sb.toString();
32:
33: return null;
34: }
35:
36: public void myClose()throws IOException
37: {
38: r.close();
39: }
40: }
41:
42: class MyBufferedReaderDemo
43: {
44: public static void main(String[] args) throws IOException
45: {
46: FileReader fr=new FileReader("abc.txt");
47:
48: MyBufferedReader mybufr=new MyBufferedReader(fr);
49:
50: String line=null;
51:
52: while((line=mybufr.myReadLine())!=null)
53: {
54: System.out.println(line);
55: }
56:
57: mybufr.myClose();
58: }
59: }
60:
黑马程序员---IO流1(FileWriter,FileReader,BufferedReader,BufferedWriter)