HTML5技术

【Java IO流】字节流和字符流详解 - 云开的立夏

字号+ 作者:H5之家 来源:H5之家 2017-09-15 15:06 我要评论( )

字节流和字符流 对于文件必然有读和写的操作,读和写就对应了输入和输出流,流又分成字节和字符流。 1.从 对文件的操作 来讲,有读和写的操作也就是输入和输出。 2.从流的 流向 来讲,有输入和输出之分。 3.从流的 内容 来讲,有字节和字符之分。 这篇文章先

字节流和字符流

对于文件必然有读和写的操作,读和写就对应了输入和输出流,流又分成字节和字符流。

1.从对文件的操作来讲,有读和写的操作——也就是输入和输出。

2.从流的流向来讲,有输入和输出之分。

3.从流的内容来讲,有字节和字符之分。

这篇文章先后讲解IO流中的字节流和字符流的输入和输出操作。

一、字节流

1)输入和输出流

首先,字节流要进行读和写,也就是输入和输出,所以它有两个抽象的父类InputStream、OutputStream。

  • InputStream抽象了应用程序读取数据的方式,即输入流。
  • OutputStream抽象了应用程序写出数据的方式,即输出流。
  • 2)读写结束

    在字节流中当读写结束,达到文件结尾时,称为EOF = End或者读到-1就读到结尾

    3)输入流基本方法

    首先我们要清楚输入流是什么。比如通过我们的键盘在文本文件上输入内容,这个过程键盘充当的就是输入流,而不是输出流。因为键盘的功能是将内容输入到系统,系统再写入到文件上。以下是输入流的基本方法read():

    .read(.read(byte[] buf,int start, int size)//读取数据到字节数组buf从buf的start位置开始存放size长度分数据

    其中in是InputStream抽象类的实例,可以发现这个方法和RandomAccessFile类中的read()方法差不多,因为两者都是通过字节来读取的。

    4)输出流基本方法

    输出流是进行写的操作,其基本操作方法是write(),可以将此方法与输入read()方法一 一去对应,更好理解。

    .write(.write(byte[] buf, int start,int size) //字节数组buf从start位置开始写size长度的字节到流

     了解了InputStream、OutputStream的基本操作方法后,再来看看它们两个的“孩子”FileInputStream和FileOutputStream。

    这两个子类具体实现了在文件上读取和写入数据的操作,日程编程中更多的是使用这两个类。

    二、FileInputStream和FileOutputStream类的使用

    -----------------FileInputStream类的使用

    1.使用read()方法读取文件

    * 读取指定文件内容,按照16进制输出到控制台 3 * 并且每输出10个byte换行 FileNotFoundException printHex(String fileName) throws IOException{ FileInputStream in=new FileInputStream(fileName); 9 int b; ((b=in.read())!=-1){ 12 if(b<=0xf){ System.out.println("0"); 15 } 16 System.out.print(Integer.toHexString(b& 0xff)+" "); 17 if(++count%10==0){ 18 System.out.println(); 19 } 20 } }

    运行结果(随便一个文件来测试的):

    注意:

    2.使用read(byte[] buf,int start, int size)方法读取文件

    上述方法只能一个一个字节读取,对于较大的文件效率太低,推荐使用这个方法来一次性读取文件。

    printHexByBytes(String fileName) throws IOException{ 2 FileInputStream in=new FileInputStream(fileName); [20*1024]; * 从in中批量读取字节,放入到buf这个字节数组中 6 * 从第0个位置开始放,最多放buf.length个 7 * 返回的是读到的字节个数 count=in.read(buf, 0, buf.length); 11 int j=1; 12 for(int i=0;i<count;i++){ 13 if((buf[i]&0xff)<=0xf){ System.out.print("0"); 16 } 17 System.out.print(Integer.toHexString(buf[i]&0xff)+ " "); 18 if(j++%10==0){ 19 System.out.println(); 20 } 21 } 22 in.close(); 23 } 24 }

    read(byte[] buf,int start, int size)返回的是读到的字节个数,即buf字节数组的有效长度,所以输出buf数组时用的长度是count而不是buf.length,因为我们不知道文件大小和数组大小的关系,上述方法适用于文件大小不超过数组大小的情况下,一次性把文件内容读取到数组里,这里就有一个问题了,如果文件大小超过数组大小,那又该如何读取才能把文件全部读完呢??

    我们知道读到-1就是读到文件末,所以还是利用while循环重复读取直到读到-1结束循环,把上述代码修改后如下:

    printHexByBytes(String fileName) throws IOException{ 2 FileInputStream in=new FileInputStream(fileName); [20*1024]; * 从in中批量读取字节,放入到buf这个字节数组中 6 * 从第0个位置开始放,最多放buf.length个 7 * 返回的是读到的字节个数 j=1; b=0; 12 while((b=in.read(buf, 0, buf.length))!=-1){ 13 for(int i=0;i<b;i++){ 14 if((buf[i]&0xff)<=0xf){ System.out.print("0"); 17 } 18 System.out.print(Integer.toHexString(buf[i]&0xff)+ " "); 19 if(j++%10==0){ 20 System.out.println(); 21 } 22 } 23 } 24 in.close(); 25 } 26 }

     好了,我们用一个大于数组的文件来测试一下结果(太长,只截图末尾):

    大家可以比较两者的不同,第二种优化后更适合日常的使用,因为无论文件大小我们都可以一次性直接读完。

    -----------------FileOutputStream类的使用

    FileOutputStream类和FileInputStream类的使用相类似,它实现了向文件中写出btye数据的方法。里面的一些细节跟FileInputStream差不多的我就不提了,大家自己可以理解的。

    1.构造方法

     FileOutputStream类构造时根据不同的情况可以使用不同的方法构造,如:

    FileOutputStream out = new FileOutputStream("demo/new1.txt");//以路径名称构造

    FileOutputStream out = new FileOutputStream("demo/new1.txt",true);

    更多内容可以查询API。

    2.使用write()方法写入文件

    write()方法和read()相似,只能操作一个字节,即只能写入一个字节。例如:

    a=10;out.write(a>>>24); 4 out.write(a>>>16); 5 out.write(a>>>8); 6 out.wirte(a);

    每次只写一个字节,显然是不效率的,OutputStream当然跟InputStream一样可以直接对byte数组操作。

    3.使用write(byte[] buf,int start, int size)方法写入文件

    意义:把byte[]数组从start位置到size位置结束长度的字节写入到文件中。

    语法格式和read相同,不多说明

    三、FileInputStream和FileOutputStream结合案例

    了解了InputStream和OutputStream的使用方法,这次结合两者来写一个复制文件的方法。

     

    1.本站遵循行业规范,任何转载的稿件都会明确标注作者和来源;2.本站的原创文章,请转载时务必注明文章作者和来源,不尊重原创的行为我们将追究责任;3.作者投稿可能会经我们编辑修改或补充。

    相关文章
    • this的用法 – JavaScript深入浅出(二) - OkayChen

      this的用法 – JavaScript深入浅出(二) - OkayChen

      2017-09-15 12:00

    • JavaScript: 使用 atan2 来绘制 箭头 和 曲线 - 救火队长

      JavaScript: 使用 atan2 来绘制 箭头 和 曲线 - 救火队长

      2017-09-14 08:04

    • 大龄程序员肉翻记录【一】 - JavaNerd

      大龄程序员肉翻记录【一】 - JavaNerd

      2017-09-13 09:01

    • Java基础精选,你答对了几道? - 小柒2012

      Java基础精选,你答对了几道? - 小柒2012

      2017-09-09 17:11

    网友点评