黑马程序员_毕向东_Java基础_DAY18-19_IO基础、字符流

----------- android培训、java培训、期待与您交流! ------------

I/O基础知识

基本概念:

I/O : Input/Output 输入输出

IO流即是输入输出流,用来处理设备之间数据的传输、流向

java对数据的操作是通过流的方式

java用于操作流的对象都在IO包中

 

分类:

按操作数据分为两种:字节流与字符流

早期都是字节流,可以处理所有数据。

后期由于文本处理是常见的处理方式,因此设置了字符流。

字符流在内部融合了码表,可以由用户来指定。

常用编码格式有:

ASCII

GBK

unicode

UTF-8

UTF-16

按流向分为:输入流、输出流

 

常见IO类

字节流抽象基类:

InputStream

OutputStream

字符流抽象基类:

Reader

Writer

由这四个基类派生出来的子类名称都以其父类名作为后缀,如:

FileInputStream

FileReader

  

字符流

Writer类

 java.io.Writer

     java.io.OutputStreamWriter

         java.io.FileWriter

 OutputStreamWriter 是一个public类,称为转换流。它是字符流通向字节流的桥梁:可使用指定的 charset 将要写入流中的字符编码成字节。它使用的字符集可以由名称指定或显式给定,否则将接受平台默认的字符集。

FileWriter是OutputStreamWriter的唯一子类,用来写入字符文件的便捷类,可以用于写入字符流。

FileWriter没有空参数构造器,必须指定目标文件。没有特有方法。

 

构造器:

FileWriter(String filename)

 创建FileWriter对象:

FileWriter fw = newFileWriter("demo.txt");

 

注意:指定的文件路径中的\需要转义。

如果指定的文件存在,则,覆盖此文件。

如果指定文件不存在,但路径存在,则会创建此文件。

如果路径不存在,则抛出异常。

创建FileWriter类对象可能会抛出java.io.IOException异常,因此要么throws要么catch。

 

fw.write("要存入的数据"); //将数据写到流中,此时还没有进文件内

fw.append();//和write差不多,但是可以使用方法调用链

fw.append("abc\r\n").append("def\r\n");

 

注意:

enter+newline with different platforms:

windows:  \r\n

mac:      \r

unix/linux: \n

 在windows下直接使用\n不能换行,而是显示一个黑方块。这就是使用记事本打开java原码文件格式混乱的原因。

 

fw.flush(); //刷新流对象中的缓冲区中的数据,清空并将其转入文件中。

close(); //关闭流资源,并刷新缓冲区。

注意:java中的输入流是调用了操作系统的功能(资源),如果不用了一定要close来释放资源。

 

文件续写:

直接使用FileWriter fw = newFileWriter("demo.txt");时覆盖源文件,如果想在文件后添加内容,则可以使用另一个构造器。

FileWriter fw = newFileWriter("demo.txt", true);

这种方式在文件存在的情况下不会覆盖原文件,而是直接再此文件的内容后添加数据。

  

FileReader类

java.lang.Object

 java.io.Reader

     java.io.InputStreamReader

         java.io.FileReader

 

构造器:

FileReader(String filename) throws FileNotFoundException

FileNotFoundException是IOException的一个子类。

当指定的文件不存在时,会抛出此异常。

FileReader fr = newFileReader("demo.txt");

System.out.println(fr.read());

fr.close();

 

注意:

read()方法用于读取一个字符,但返回的字符是int型的,所以需要强制类型转换(char)fr.read()。

 read()方法是依次向后读取,如果读到末尾(文件的结束标记),则返回-1。

 

读取方式:(一次读一个字符)

int ch = 0;

while((ch = fr.read()) != -1)){

       fw.write(ch);

}

  

另一种读取方式:(一次读2KB)

char[] buffer = new char[1024];

int len = 0;

while((len = fr.read(buffer)) != -1){

       fw.write(buffer,0, len);

}

 关于IOException 的处理:

可以直接使用throw newRuntimeException();的方式来强制结束程序。

打开多个流时,在finally块中要依次关闭。

 

练习:

 //: IOExceptionDemo.java
//IO异常处理基本格式
 
import java.io.FileWriter;
import java.io.IOException;
 
class IOExceptionDemo
{
       publicstatic void main(String[] args)
       {
              FileWriterfw = null;
              try{
                     fw= new FileWriter("demo.txt");
                     fw.write("我整个人都斯巴达了!\r\n");
                     fw.append("我整个人都斯巴达了!\r\n").append("这就是斯巴达!!\r\n");
              }
              catch(IOExceptione){
                     System.out.println("发生了IO异常!" +e.toString());
              }
              finally{
                     try{
                            if(fw!= null)
                                   fw.close();
                     }
                     catch(IOExceptione){
                            System.out.println("发生了IO异常!" +e.toString());
                     }
              }
       }
}

  

//: FileReaderDemo.java
//读取文本文件
 
import java.io.FileReader;
import java.io.IOException;
 
class FileReaderDemo {
       publicstatic void main(String[] args) {
              FileReaderfr = null;
              try{
                     fr= new FileReader("demo.txt");
                     char[]buffer = new char[1024];
                     intnum = 0;
                     while((num= fr.read(buffer)) != -1)
                            System.out.println(newString(buffer, 0, num));
              }
              catch(IOException e){
                     System.out.println("发生了IO异常::" +e.toString());
              }
              finally{
                     try{
                            if(fr!= null)
                                   fr.close();
                     }
                     catch(IOException e){
                            System.out.println("发生了IO异常::" +e.toString());
                     }
              }
       }
}
 

//: CopyTextDemo.java
//分别使用单字符的buf,和char[]进行文本文件的复制
 
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
 
class CopyTextDemo{
       publicstatic void main(String[] args) {
              copyChar();
              copyCharArr();
       }
       publicstatic void copyChar(){
              FileReaderfr = null;
              FileWriterfw = null;
              try{
                     fr= new FileReader("demo.txt");
                     fw= new FileWriter("d:\\demo.txt");
                     intch = 0;
                     while((ch = fr.read()) != -1)
                            fw.write(ch);
              }
              catch(IOException e){
                     System.out.println("发生了IO异常::" +e.toString());
              }
              finally{
                     try{
                            if(fr != null)
                                   fr.close();
                     }
                     catch(IOException e){
                            System.out.println("发生了IO异常::" +e.toString());
                     }                   
                     try{
                            if(fw!= null)
                                   fw.close();
                     }
                     catch(IOException e){
                            System.out.println("发生了IO异常::" +e.toString());
                     }
              }
       }
 
       publicstatic void copyCharArr(){
              FileReaderfr = null;
              FileWriterfw = null;
              try{
                     fr= new FileReader("demo.txt");
                     fw= new FileWriter("d:\\demo.txt", true);
                     char[]buffer = new char[1024];
                     intnum = 0;
                     while((num = fr.read(buffer)) != -1)
                            fw.write(buffer,0, num);
              }
              catch(IOException e){
                     System.out.println("发生了IO异常::" +e.toString());
              }
              finally{
                     try{
                            if(fr != null)
                                   fr.close();
                     }
                     catch(IOException e){
                            System.out.println("发生了IO异常::" +e.toString());
                     }                   
                     try{
                            if(fw!= null)
                                   fw.close();
                     }
                     catch(IOException e){
                            System.out.println("发生了IO异常::" +e.toString());
                     }
              }
       }
}

字符流缓冲区:

BufferedWriter

 java.lang.Object

 java.io.Writer

     java.io.BufferedWriter

它没有空参数构造器,在创建对象时必须指定目标Writer对象。

这是因为缓冲区是为了提高流的操作效率而出现的。

所以在创建缓冲区之前,必须先有流对象。

 

构造器:

BufferedWriter(Writer out)

         创建一个使用默认大小输出缓冲区的缓冲字符输出流。

BufferedWriter(Writer out, int sz)

         创建一个使用给定大小输出缓冲区的新缓冲字符输出流。

 

方法:

 voidclose()

         关闭此流,但要先刷新它。

 voidflush()

         刷新该流的缓冲。

 void newLine()

         写入一个行分隔符。

 voidwrite(char[] cbuf, int off, int len)

         写入字符数组的某一部分。

 voidwrite(int c)

         写入单个字符。

 voidwrite(String s, int off, int len)

         写入字符串的某一部分。

write方法可以用于写入字符、字符串、字符数组

 

BufferedReader

 java.lang.Object

 java.io.Reader

     java.io.BufferedReader

 使用上与BufferedWriter大致相同。

 包含特殊方法:

String readLine()读取一个文本行。

 

练习:

//: BufferedTest.java
//使用字符缓冲流进行文本文件复制操作
 
import java.io.*;
 
class BufferedTest
{
       publicstatic void main(String[] args)
       {
              BufferedReaderbuffr = null;
              BufferedWriterbuffw = null;
              try
              {
                     buffr= new BufferedReader(new FileReader("demo.txt"));
                     buffw= new BufferedWriter(new FileWriter("buffDemo.txt"));
                     Stringstr = null;
                     while((str= buffr.readLine()) != null){
                            buffw.write(str);
                            buffw.newLine();
                            buffw.flush();
                     }
              }
              catch(IOException e)
              {
                     thrownew RuntimeException("文件复制发生错误");
              }
              finally{
                     if(buffr!= null){
                            try
                            {
                                   buffr.close();
                            }
                            catch(IOException e)
                            {
                                   thrownew RuntimeException("关闭输入流时发生错误");
                            }
                     }
                     if(buffw!= null){
                            try
                            {
                                   buffw.close();
                            }
                            catch(IOException e)
                            {
                                   thrownew RuntimeException("关闭输出流时发生错误");
                            }
                     }
              }
       }
}

 

自定义类模拟字符缓冲流: 

//: MyBufferedReaderTest.java
//使用自定义类模拟BufferedReader功能
 
import java.io.*;
 
class MyBufferedReader
{
       Readerfr;
       MyBufferedReader(Readerfr){
              this.fr= fr;
       }
       publicString readLine() throws IOException{
              StringBuildersb = new StringBuilder();
              intch = 0;
              while((ch= fr.read()) != -1){
                     if(ch== '\r')
                            continue;
                     if(ch== '\n')
                            returnsb.toString();
                     else
                            sb.append((char)ch);
              }
              if(sb.length()!= 0)
                     returnsb.toString();
              returnnull;
       }
       publicvoid close() throws IOException{
              fr.close();
       }
}
 
class MyBufferedReaderTest
{
       publicstatic void main(String[] args)
       {
              MyBufferedReaderbuffr = null;
              BufferedWriterbuffw = null;
              try
              {
                     buffr= new MyBufferedReader(new FileReader("demo.txt"));
                     buffw= new BufferedWriter(new FileWriter("123.txt"));
                     Stringstr = null;
                     while((str= buffr.readLine()) != null){
                            buffw.write(str);
                            buffw.newLine();
                            buffw.flush();
                     }
              }
              catch(IOException e)
              {
                     thrownew RuntimeException("文件复制发生错误");
              }
              finally{
                     if(buffr!= null){
                            try
                            {
                                   buffr.close();
                            }
                            catch(IOException e)
                            {
                                   thrownew RuntimeException("关闭输入流时发生错误");
                            }
                     }
                     if(buffw!= null){
                            try
                            {
                                   buffw.close();
                            }
                            catch(IOException e)
                            {
                                   thrownew RuntimeException("关闭输出流时发生错误");
                            }
                     }
              }
       }
}

 

装饰设计模式:

当想要对已有的对象进行功能增强时,

可以定义一个新类,将已有对象传入(组合),基于已有的功能,并提供加强功能。

那么自定义的该类称为装饰类。

 

装饰模式比继承要灵活,避免了继承体系臃肿,而且降低了类与类之间的关系。

装饰类因为增强已有对象,具备的功能和已有的是相同的,只不过提供了更强的功能。

所以装饰类和被装饰类通常都属于一个体系中,表示只要只某某的子类,我全能进行增强。

 

事实上字符缓冲流使用的就是装饰设计模式。

 

LineNumberReader

 

java.lang.Object

 java.io.Reader

     java.io.BufferedReader

         java.io.LineNumberReader

 

LineNumberReader是BufferedReader的子类,包含父类的所有功能。

在此基础上,还添加了两个新方法:

 

int getLineNumber() //获取当前行号

void setLineNumber() //设置当前行号

 

设计自定义类模拟LineNumberReader的功能:

//: MyLineNumberReader.java
//自定义类模拟LineNumberReader类
 
import java.io.*;
 
class MyLineNumberReader extendsMyBufferedReader
{
       privateint lineNumber = 0;
 
       publicMyLineNumberReader(Reader r){
              super(r);
       }
       publicint getLineNumber(){
              returnlineNumber;
       }
       publicvoid setLineNumber(int num){
              this.lineNumber= num;
       }
 
       publicString readLine() throws IOException{
              lineNumber++;
              returnsuper.readLine();
       }
 
       publicstatic void main(String[] args)
       {
              MyLineNumberReadermyline = null;
              BufferedWriterbw = null;
              try
              {
                     myline= new MyLineNumberReader(new FileReader("demo.txt"));
                     bw= new BufferedWriter(new FileWriter("myline.txt"));
                     Stringstr = null;
                     while((str = myline.readLine()) != null)
                     {
                            bw.write(myline.getLineNumber()+ ": " + str);
                            bw.newLine();
                            bw.flush();
                     }
              }
              catch(IOException e)
              {
                     thrownew RuntimeException("读写文件时发生错误");
              }
              finally{
                     if(myline!= null){
                            try
                            {
                                   myline.close();
                            }
                            catch(IOException e)
                            {
                                   thrownew RuntimeException("关闭输入流时发生错误");
                            }
                     }
                     if(bw!= null){
                            try
                            {
                                   bw.close();
                            }
                            catch(IOException e)
                            {
                                   thrownew RuntimeException("关闭输出流时发生错误");
                            }
                     }
              }
       }
}


----------- android培训、java培训、期待与您交流! ------------

你可能感兴趣的:(黑马自学课程)