IO流
IO流用来处理设备之间的数据传输
java对数据的操作是过流的方式
流按操作数据分为两种:字节流与字符流
流按流向分为:输入流,输出流。
IO流常用基类
字节流的抽象基类:InputStream OutputStream
字符流的抽象基类:Reader,Writer
由这四个类派生出来的子类名称都是以其父类作为子
类名的后缀。
如InputStream 的子类 FileInpuStream
Reader的子类FileReader
数据的最常见的形式是:文件
字符读取缓冲区:
class BufferedReaderDemo { //创建一个读取流对象和文件相关联 FileReader fr=new FileReader("buf.txt"); //为了提高效率,加入缓冲技术,将字符流取对象作为参数传给缓冲对象的构造函数。 //只要是文本文件,都是以行的形式存在的。 //readLine返回的是该行的字符串,不包含任何行终止符,如果已经达到流的末尾,则返回null. BufferedReader bufr=new BufferedReader(fr); String line=null; while(line=bufr.readLine()!=null) { System.out.println(line); } bufr.close(); }通过缓冲区复制一个.java文件到.txt文件:
class{ public static void main(String[] args){ BufferedReader bufr=null; BufferedWriter bufw=null; try{ bufr=new BufferedReader(new FileReader("bufferwriteDemo.java")); bufw=new BufferedWriter(new FilerWriter("bufwriter.txt")); 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(bufr!=null) bufr.close(); }catch(IOException e){ throw new RuntimeException("写入失败"); } } } }readline方法的原理:无论是读一行或者读取多个字符,其实都是在硬盘上一个一个的读取,所以最终使用的还是read方法一次读一个的方法。读到一个字符以后只是把它存到一行里,当读到\r,因为它不读任何终止符, 这个时候,把数组里已经存好的字符返回出来。然后接着往下读。一直到读完。。readline比read方法高效。 做一个MyBufferedReader,自定义一个类中包含一个功能和readLine一致的方法,来模拟一个BufferedReader:
import java.io.*; class MyBufferedReader{ private FileReader r; MyBufferedReader(FileReader r) throws IOException{//抛出异常,下面就不用try,catch了 this.r=r;//实例化 } //可以一次读一行数据的方法 public String myReadLine(){ //定义一个临时容器,原Buffered装的是一个字符数组。定义一个StringBuilder容器,因为最终还是要将数据变成字符串。 StringBuilder sb=new StringBuilder(); int ch=0; while((ch=r.readLine())!=-1){ if(ch=='\r') continue; if(ch=='\n') return sb.toString(); else sb.append((char)ch);//在指定元素结尾插入字符 } if(sb.length()!=0) return sb.toString(); return null; } public void myClose()throws IOException{ r.close();//模拟关闭流 } } class MyBufferedReaderDemo{ public static void main(String [] args){ FileReader fr=new FileReader("buf.txt"); MyBufferedReader myBuf=new MyBufferedReader(fr);// String line=null; while((line=myBuf.myReadLine()!=null){ System.out.println("line"); } myBuf.myClose(); } }装饰者设计模式: 当想要对已有的对象进行功能增强时,可以定义类,将已有对象传入,基于已有的功能,并提供加强功能,那么自定义的该类称为装饰类。装饰者通常会通过构造对象方法接收被接收的对象,并基于被装饰的对象的功能。并提供更强的功能。
class Person{ public void chifan(){ System.out.println("吃饭"); } } class SuperPerson{ private Person p; SuperPersonn(Person p){ this.p=p; } public void superChifan(){ System.out.println("吃甜点"); p.chifan(); System.out.println("吃饭"); System.out.println("打牌"); } } class PersonDemo{ public static void main(String [] args){ Person p=new Person(); //p.chifan(); SuperPerson sp=new SuperPerson(p); sp.superChifan(); } }装饰和继承的区别 MyReader//专门用于读取数据的类 继承: |MyTextReader 文本读取 |MYBufferedTextReader |MyMediaReader 媒体读取 |MyBufferedMediaReader |MyDataReader |MyBufferedDataReader
class MyBufferReader{ MyBufferReader(MyTextReader text){ } MyBufferReader(MyBufferedMediaReader media){ } }上面这个类的扩展性极差,找到其参数的共同类型,可以提高扩展性 下面这个就是装饰设计模式,可以将这个体系优化 |MyTextReader 文本读取 |MyMediaReader 媒体读取 |MyDataReader |MyBufferReader 装饰模式比继承要灵活,避免了继承了体系的冗余,而且降低了类与类之间的关系 装饰类因为增强已有对象,具备的功能和已有的是相同的,只不过提供了更强功能,所以装饰类和被装饰类通常是都属于一个体系中的。 MyReader//专门读取数据的类
class MyBufferReader{ MyBufferReader(MyReader r){ } }