黑马程序员_IO流操作1

来源:互联网 发布:sla打印机 知乎 编辑:程序博客网 时间:2024/05/18 00:47

<span style="font-family: Arial, Helvetica, sans-serif;">       ------<a href="http://www.itheima.com" target="blank">Java培训、Android培训、iOS培训、.Net培训</a>、期待与您交流! -------</span>

       在学习Java的SE基础部分时,一重要知识点就是IO流操作。这是因为流是一组有顺序的,有起点和终点的字节集合,是对数据传输的总称或抽象。即数据在两设备间的传输称

为流,流的本质是数据传输,根据数据传输特性将流抽象为各种类,方便更直观的进行数据操作。

       Java中IO流可以根据处理数据类型的不同分为:字符流和字节流;根据数据流向不同分为:输入流和输出流 。

      那么什么时候用字符流,什么时间用字节流呢,通过学习和自己的理解,简单的总结为一句话,所以传输都可以用字节流,文字用字符流,其他(图片、文件)用字节流处

理。这只是我个人的理解,如果有误还请好心的你指正。

1.输入字节流InputStreamIO 中输入字节流的继承图可见上图,可以看出:

InputStream 是所有的输入字节流的父类,它是一个抽象类。ByteArrayInputStream、StringBufferInputStream、FileInputStream 是三种基本的介质流,它们分别从Byte 数组、StringBuffer、和本地文件中读取数据。ObjectInputStream 和所有FilterInputStream 的子类都是装饰流(装饰器模式的主角)。

OutputStream 是所有的输出字节流的父类,它是一个抽象类。ByteArrayOutputStream、FileOutputStream 是两种基本的介质流,它们分别向Byte 数组、和本地文件中写入数据。PipedOutputStream 是向与其它线程共用的管道中写入数据,ObjectOutputStream 和所有FilterOutputStream 的子类都是装饰流。

    

           

         这张图是Java流操作有关的类或接口。下面这张图将详细解释Java流类结构:


         话不多说,上代码,首先看看字节流吧。代码的思想也是由浅入深,最终变成常用形式。

package com.vince.bytestream;/** * 字节流输入 * */import java.io.File;import java.io.FileInputStream;import java.io.FileNotFoundException;import java.io.IOException;import java.io.InputStream;public class InputStreamDemo {/** * 字节输入流读取方式一:每一次读取一个字节 * */public static void read1(){try {//构造一个字节输入流对象InputStream in = new FileInputStream("e:\\1.txt");int b = -1;//-1表示没有数据while((b=in.read())!=-1){ System.out.print((char)b);}//关闭in.close();} catch (FileNotFoundException e) {e.printStackTrace();} catch (IOException e) {e.printStackTrace();}}/** * 字节输入流读取方式二:一次性读取所有字节 * */public static void read2(){try {//构造一个字节输入流对象File f = new File("e:\\1.txt");InputStream in = new FileInputStream(f);//根据文件的大小构造字节数组byte[] bytes = new byte[(int)f.length()];int len = in.read(bytes);System.out.println(new String(bytes));System.out.println("len="+len);//关闭in.close();} catch (FileNotFoundException e) {e.printStackTrace();} catch (IOException e) {e.printStackTrace();}}/** * 字节输入流读取方式三:每次读取指定大小的字节 * */public static void read3(){try {//构造一个字节输入流对象File f = new File("e:\\1.txt");InputStream in = new FileInputStream(f);//根据文件的大小构造字节数组byte[] bytes = new byte[10];int len = -1;//每次读取的实际长度StringBuilder sb = new StringBuilder();while((len = in.read(bytes))!=-1){sb.append(new String(bytes,0,len));//sb.append(new String(bytes));如果用这个会有问题,//数组内容是覆盖,最后一次可能用不了10个,只覆盖3个//那么后面6个将不是我们需要的愿内容}//关闭in.close();System.out.println(sb);} catch (FileNotFoundException e) {e.printStackTrace();} catch (IOException e) {e.printStackTrace();}}public static void main(String[] args) {read2();//System.out.println("success");}}

package com.vince.bytestream;/** * 字节流输出 * */import java.io.FileNotFoundException;import java.io.FileOutputStream;import java.io.IOException;import java.io.OutputStream;public class OutputStreamDemo {/** * 字节输出流的方式一:每次输出一个字节 * */public static void write1(){try {//创建一个文件字节输出流OutputStream out = new FileOutputStream("e:\\1.txt");String info = "Hello,IO";byte[] bytes = info.getBytes();for(int i=0;i<bytes.length;i++){out.write(bytes[i]);//向文件中输出}//关闭流out.close();} catch (FileNotFoundException e) {e.printStackTrace(); } catch (IOException e) {e.printStackTrace();}}/** * 字节输出流的方式二:每次输出指定大小的字节 * */public static void write2(){try {//创建一个文件字节输出流OutputStream out = new FileOutputStream("e:\\1.txt");String info = "Hello,xiaobai";byte[] bytes = info.getBytes();out.write(bytes);//输出一个字节数组//关闭流out.close();} catch (FileNotFoundException e) {e.printStackTrace(); } catch (IOException e) {e.printStackTrace();}}/** * 字节输出流的方式二:每次输出指定大小的字节.追加 * */public static void write3(){try {//创建一个文件字节输出流OutputStream out = new FileOutputStream("e:\\1.txt");//("e:\\1.txt,true")表示追加String info = "Hello,xiaobai";byte[] bytes = info.getBytes();out.write(bytes,0,5);//输出一个字节数组中指定范围的字节//关闭流out.close();} catch (FileNotFoundException e) {e.printStackTrace(); } catch (IOException e) {e.printStackTrace();}}public static void main(String[] args) {//write1();//write2();write3();System.out.println("success");}}
<span style="white-space:pre"></span>字节流看完了,接下来我们看看字符流。
<span style="white-space:pre"></span>字节流与字符流有什么区别呢?对于一个纯文本文件,字符流可以读取,<span style="font-family: Arial, Helvetica, sans-serif;">可以如果用字节流对UTF-8或Uicode进行读取可能会出现乱码,因此就有了专门对文本操作的字节流。字节流分为两类:Reader和Writer。</span>
 
<span style="white-space:pre">在上面的继承关系图中可以看出:</span>
<span style="white-space:pre"></span>Reader
<span style="font-family: Arial, Helvetica, sans-serif;">1、Reader 是所有的输入字符流的父类,它是一个抽象类。</span><span style="white-space:pre">2、CharReader、StringReader 是两种基本的介质流,它们分别将Char 数组、String中读取数据。PipedReader 是从与其它线程共用的管道中读取数据。3、BufferedReader 很明显就是一个装饰器,它和其子类负责装饰其它Reader 对象。4、FilterReader 是所有自定义具体装饰流的父类,其子类PushbackReader 对Reader 对象进行装饰,会增加一个行号。5、InputStreamReader 是一个连接字节流和字符流的桥梁,它将字节流转变为字符流。FileReader 可以说是一个达到此功能、常用的工具类,在其源代码中明显使用了将FileInputStream 转变为Reader 的方法。我们可以从这个类中得到一定的技巧。Reader 中各个类的用途和使用方法基本和InputStream 中的类使用一致。后面会有Reader 与InputStream 的对应关系</span>
<span style="white-space:pre"></span>
<span style="white-space:pre"></span>Writer
<span style="white-space:pre">1、Writer 是所有的输出字符流的父类,它是一个抽象类。2、CharArrayWriter、StringWriter 是两种基本的介质流,它们分别向Char 数组、String 中写入数据。PipedWriter 是向与其它线程共用的管道中写</span>   <span style="white-space:pre">入数据,3、BufferedWriter 是一个装饰器为Writer 提供缓冲功能。4、PrintWriter 和PrintStream 极其类似,功能和使用也非常相似。5、OutputStreamWriter 是OutputStream 到Writer 转换的桥梁,它的子类FileWriter 其实就是一个实现此功能的具体类(具体可以研究一SourceCod</span>   <span style="white-space:pre">e)。功能和使用和OutputStream 极其类似,后面会有它们的对应图。</span>
</pre><pre name="code" class="java"><span style="white-space:pre"></span>通过下面的代码,加深Reader和Writer的使用吧。读者可以把以下代码复制下来到自己的java工具中运行调试。
<pre name="code" class="java"><span style="white-space:pre">package IO字符流;import java.io.FileNotFoundException;import java.io.FileReader;import java.io.IOException;</span>
<span style="white-space:pre"></span><pre name="code" class="java">public class The_1_Reader {public static void main(String[] args) {//创建一个文件读取对象,和指定名称的文件相关联。//要保证该文件是已经存在的,如果不存在,会发生异常FileReader fr = null;try {fr = new FileReader("e:\\text1.txt");//调用读取流对象的read方法//int ch;//一次读一个字符,而且会依次往下读//ch = fr.read();//System.out.println("ch="+(char)ch);int len = -1;while((len = fr.read())!=-1){System.out.print("len="+(char)len);//注意print 如果println数据超出1024会换行}} catch (FileNotFoundException e) {e.printStackTrace();} catch (IOException e) {e.printStackTrace();}}}


package IO字符流;import java.io.FileWriter;import java.io.IOException;/** * IO流 * 流按操作数据分为两种:字节流与字符流 * 流按流向分为:输入流、输出流 *  * 字节流的抽象基类 * InputStream,OutputStream *  字符流的抽象基类 *  Reader,Writer *  这四个类派生出来的子类名称都是以其父类名作为子类名的后缀,前缀名为该类的功能 *  如:InputStream 的子类 FileInputStream *         Reader  的子类  FileReader *    * */public class The_1_Writer {public static void main(String[] args) {//在外面进行引用,在try中进行初始化FileWriter fw = null;try {//创建一个FileWriter对象。该对象已被初始化就必须要明确被初始化的文件//而且该文件会被创建到指定的目录下,如果该目录下已有同名文件,将被覆盖//其实该步就是在明确数据存放的目的地。 fw = new FileWriter("e:\\text1.txt");//调用write()方法,将字符串写入到流中fw.write("abcde");//刷新流对象中缓冲的数据。//将数据刷到目的地中。fw.flush();} catch (IOException e) {e.printStackTrace();} finally{try {//关闭流资源,但是关闭前会刷新一次内部的缓冲中的数据//将数据刷新到目的地中//和flush区别:flush刷新后,流可以继续使用,close刷新后,会关闭流if(fw!=null)fw.close();} catch (IOException e) {e.printStackTrace();}}}}


0 0
原创粉丝点击