黑马程序员——Java基础——IO流

第一讲  IO概述

1概述:IO流:输入(Input与Output流)

2特点:

  a、IO流用于数据传输;  b、按操作分为字节流与字符流  c、按流向分:输入流和输出流

3、常用IO流的基类

1)字节流的基类:InputStream和OutpuStream

2)字符流的基类:Reader和Writer

 

第二讲  字符流

一、简述

  1、字符流的对象融合了编码表。使用的是默认的编码

  2、字符流只能用于文字处理,而字节流可以处理其他:

  3、下列把FileWriter和FileReader一起讲

 1 package System;

 2 /*
 3  * 将文件做复制
 4  */
 5 import java.io.*;
 6 public class CopyTest {
 7     public static void main(String[] args){
 8         int s1=(int) System.currentTimeMillis();
 9         copy_1();
10         int s2=(int) System.currentTimeMillis();
11         copy_2();
12         int s3=(int) System.currentTimeMillis();
13         System.out.println(s2-s1+"毫秒");//顺便计算下时间
14         System.out.println(s3-s2+"毫秒");    //顺便计算下时间
15     }
16 
17     private static void copy_1() {
18         FileWriter fw=null;
19         FileReader fr=null;
20         try {
21             fw=new FileWriter("xxx_1.txt");//创建输入的文件xxx_1 
22             fr=new FileReader("TestDemo.java"); //创建要输出的流
23             for(int ch=0;(ch=fr.read())!=-1;){//一个字节一个自己读并输出
24                 fw.write((char)ch);
25             }
26         } catch (IOException e) {
27             throw new RuntimeException("毒性"); 
28         }finally{
29             if(fr!=null)
30                 try {
31                     fr.close();
32                 } catch (Exception e2) {
33                     // TODO: handle exception
34                 }
35             if(fw!=null)
36                 try {
37                     fw.close();
38                 } catch (Exception e2) {
39                     // TODO: handle exception
40                 }
41         }
42         
43     }
44 
45     private static void copy_2() {
46         FileWriter fw=null;
47         FileReader fr=null;
48         try {
49             fw=new FileWriter("xxx_2.txt"); 
50             fr=new FileReader("TestDemo.java"); 
51             char[] buff=new char[1024];//第二种方法是字符数组的形式读取并输出,一般创建1024整数倍的数组
52             for(int len=0;(len=fr.read(buff))!=-1;){//fr.read(buff)指定是中buff的长度
53                 fw.write(new String(buff,0,len));//记住这里新创了个String把读出来的buff从0到len
54             }
55         } catch (IOException e) {
56             throw new RuntimeException("毒性"); 
57         }finally{
58             if(fr!=null)
59                 try {
60                     fr.close();
61                 } catch (Exception e2) {
62                     // TODO: handle exception
63                 }
64             if(fw!=null)
65                 try {
66                     fw.close();
67                 } catch (Exception e2) {
68                     // TODO: handle exception
69                 }
70         
71         }
72     }
73

字符缓冲流:

1、缓冲流的出现为了提高读写效率,所以在缓冲区创建钱就先创建对象。

使用复制一个java文件说明使用方法:

import java.io.*;
//使用缓冲流的方法复制文件来学习使用的格式
public class BuferedTest {
    public static void main(String[] args){
        BufferedWriter bufw=null;
        BufferedReader bufr=null;
        try {
            bufw=new BufferedWriter(new FileWriter("xx.txt"));//无法添加ture
            bufr=new BufferedReader(new FileReader("TestDemo.java"));
            String line=null;
            while(!((line=bufr.readLine())==null)){
                bufw.write(line);
                bufw.newLine();//记得换行
                bufw.flush();
            }
            
        } catch (IOException e) {
            throw new RuntimeException("书写错误");
        }finally{
            try {
                if(bufr!=null)
                    bufr.close();
            } catch (IOException e) {
                throw new RuntimeException("读取错误");
            }
            try {
                if(bufw!=null)
                    bufw.close();
            } catch (IOException e) {
                throw new RuntimeException("读取错误");
            }                        
        }                
    }
}

3、自定义BufferedReader

原理:

  可根据BufferedReader类中特有一行一行读取原理,分析思路如下

思路:

  1:它的构造函数中参数是FileReader,所以一创建就有FileReader;

  2、在执行ReadLine时,先需要一个容器(StringBuilder)容纳一行的数据,和int容纳一个字节数据

    然后只在出现、n是返回

  3、最后关闭的是close()的动作就是关闭里面的FileReader;

装饰设计模式:

简述:

当想要对已有的对象进行功能增强时,可以定义类,将有已有对象作为构造函数的参数传入,基于已有对象的功能进行加强,那么自定义的该类称之装饰类

我们上面的MyBufferedReader就装饰设计模式的好例子。

为什么使用装饰而不是继承来增加功能?

  a、装饰模式避免了继承体现的臃肿

  b、装饰类因为是增强已有对象,所以必然需要与已有对象相同的功能,所以装饰类和被装饰类是同一个体现

  c、增加者与被增强者的继承结构转为组合结构

 1 /*
 2  自定义BufferedReader
 3 原理:
 4   可根据BufferedReader类中特有一行一行读取原理,分析思路如下
 5 思路:
 6   1:它的构造函数中参数是FileReader,所以一创建就有FileReader;
 7 
 8   2、在执行ReadLine时,先需要一个容器(StringBuilder)容纳一行的数据,和int容纳一个字节数据
 9 
10     然后只在出现、n是返回
11   3、最后关闭的是close()的动作就是关闭里面的FileReader;
12  */
13 import java.io.*;
14 
15 import javax.management.RuntimeErrorException;
16 class MyBufferedReader extends Reader{
17     private Reader fr;//等于一创建就有这个fr的FileReader
18     MyBufferedReader(Reader fr){//从FileReader(子类)变Reader(父类),多态增加使用范围
19         this.fr=fr;
20     }
21     
22 //    一下是自定义的读取一行的方法myReadLine
23     public String myReadLine() throws IOException{
24 //        一个容器StringBuilder和字节容器int
25         StringBuilder sb=new StringBuilder();
26         int ch=0;
27         while((ch=fr.read())!=-1){//返回负一时就跳出循环
28             if(ch==‘\r‘)//如果换行符,则继续
29                 continue;
30             if(ch==‘\n‘)//如果回车符
31                 return sb.toString();
32             else
33                 sb.append((char)ch);                
34         }
35         if(sb.length()!=0)
36             return sb.toString();
37         return null;
38     }
39 //    父类中的close也是抽象方法
40     public void close()throws IOException{//实际上就是关闭FileReader
41         fr.close();
42     }
43 
44 //    复写父类Reader中的抽象方法
45     public int read(char[] cbuf, int off, int len) throws IOException {
46         return fr.read(cbuf,off,len);
47     }
48 }
49 public class MyBufferedReaderDemo {
50     public static void main(String[] args){
51         //使用方法和原方法一样
52         MyBufferedReader mbr=null;
53         try {
54             mbr=new MyBufferedReader(new FileReader("TestDemo.java"));
55             String line=null;
56             while((line=mbr.myReadLine())!=null){//一行的数据已经给了line
57                 System.out.println(line);
58             }
59         } catch (IOException e) {
60             throw new RuntimeException("数据读取失败");
61         }
62         finally{
63             try {
64                 if(mbr!=null)
65                     mbr.close();
66             } catch (IOException e2) {
67                 throw new RuntimeException("关闭流失败");
68             }
69         }
70         
71     }
72 }

 练习:带行数的缓冲流,LineNumber的运用

 1 import java.io.*;
 2 
 3 import javax.management.RuntimeErrorException;
 4 public class LinewNumberReaderDemo {
 5     public static void main(String[] args) {
 6         FileReader fr=null;
 7         LineNumberReader lnr=null;//可以带行数的缓冲流
 8         try {
 9             fr=new FileReader("TestDemo.java");
10             lnr=new LineNumberReader(fr);
11             
12             String line=null;
13             lnr.setLineNumber(50);//设置从50开始数
14             
15             while((line=lnr.readLine())!=null){
16                 System.out.println(lnr.getLineNumber()+":"+line);//getLineNumber就是
17                 //得到行数
18             }
19         } catch (IOException e) {
20             throw new RuntimeException("数据输入有误");
21         }
22         finally{
23             try {
24                 if(lnr!=null)
25                     lnr.close();
26             } catch (Exception e2) {                
27             }            
28         }        
29     }
30 }

 

 

 

 

 

 

 

 

 

 

 

郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。