说说JAVA I/O流的那些事

来源:互联网 发布:freecad python 编辑:程序博客网 时间:2024/05/23 22:36

    

Java所有的流类位于java.io包中,都分别继承字以下四种抽象流类型。

 字节流字符流输入流InputStreamReader输出流OutputStreamWriter

1.继承自InputStream/OutputStream的流都是用于向程序中输入/输出数据,且数据的单位都是字节(byte=8bit),如图,深色的为节点流,浅色的为处理流。

 

2.继承自Reader/Writer的流都是用于向程序中输入/输出数据,且数据的单位都是字符(2byte=16bit),如图,深色的为节点流,浅色的为处理流。

 3、按照流是否直接与特定的地方(如磁盘、内存、设备等)相连,分为节点流和处理流两类。 
  
节点流:可以从或向一个特定的地方(节点)读写数据。如FileReader 
  处理流:是对一个已存在的流的连接和封装,通过所封装的流的功能调用实现数据读写。如BufferedReader。处理流的构造方法总是要带一个其他的流对象做参数。一个流对象经过其他流的多次包装,称为流的链接。 
  常用的节点流 
  父 类 InputStream OutputStream Reader Writer 
  文 件 *FileInputStream FileOutputStrean FileReader FileWriter 文件进行处理的节点流 
  数 组 *ByteArrayInputStream ByteArrayOutputStream CharArrayReader CharArrayWriter 对数组进行处理的节点流(对应的不再是文件,而是内存中的一个数组) 
  字符串 *无  无 StringReader StringWriter 对字符串进行处理的节点流 
  管 道 *PipedInputStream PipedOutputStream PipedReader PipedWriter 对管道进行处理的节点流 
  常用处理流(关闭处理流使用关闭里面的节点流) 
  父 类 InputStream OutputStream Reader Writer 
  缓冲流 *BufferedImputStrean BufferedOutputStream BufferedReader BufferedWriter ----需要父类作为参数构造,增加缓冲功能,避免频繁读写硬盘,可以初始化缓冲数据的大小,由于带了缓冲功能,所以就写数据的时候需要使用flush方法咯 
  转换流 *InputStreamReader OutputStreamWriter- 要inputStream或OutputStream作为参数,实现从字节流到字符流的转换 
  数据流 *DataInputStream DataOutputStream -提供将基础数据类型写入到文件中,或者读取出来,为什么要有这个流呢?看这样的分析,如果没有这种流的话,有一个long,本身只占8个字节,如果我要写入到文件,需要转成字符串,然后在转成字符数组,那空间会占用很多,但是有了这种流之后就很方便了,直接将这8个字节写到文件就完了。。是不是既节约了内存空间有让程序写起来更加方便简单了呐。写倒是很简单,但是读取的时候就注意了,根据读取的数据类型,指针会往下移,所以你写的顺序必须要和读的顺序一致才能完成你正确的需求。 
   对象流*ObjectInputStream ObjectOutputStream

  打印流*PrintStream,PrintWriter这类流在写入的时候有自动flush的功能,所以你不需要每打印一个东西都flush一次)

  System.In====InputStream 
      System.Out===PrintStream 



InputStream的方法:

available():返回下一次对此输入流调用的方法可以不受阻塞第从此输入流读取(或跳过)的估计剩余字节数。

简单说,就是返回实际可读的字节数。但是需要注意的是,java虚拟机中的字符是Unicode编码,占两个字符,假如一个txt文档的内容abcde是ASCII编码,那么每个字符就是一个字节,所以供5个字节。注意class中的编码也不是Unicode的,而是utf-8的。


read()与read(byte[] b)

read() :  从输入流中读取数据的下一个字节,返回0255范围内的int字节值。如果因为已经到达流末尾而没有可用的字节,则返回-1。在输入数据可用、检测到流末尾或者抛出异常前,此方法一直阻塞。

read(byte[] b) :  从输入流中读取一定数量的字节,并将其存储在缓冲区数组 b 中。以整数形式返回实际读取的字节数。在输入数据可用、检测到文件末尾或者抛出异常前,此方法一直阻塞。

如果 b 的长度为 0,则不读取任何字节并返回 0;否则,尝试读取至少一个字节。如果因为流位于文件末尾而没有可用的字节,则返回值 -1;否则,至少读取一个字节并将其存储在 b 中。

将读取的第一个字节存储在元素 b[0] 中,下一个存储在 b[1] 中,依次类推。读取的字节数最多等于的长度。设 k 为实际读取的字节数;这些字节将存储在 b[0]  b[k-1] 的元素中,不影响 b[kb[b.length-1] 的元素。

 

由帮助文档中的解释可知,read()方法每次只能读取一个字节,所以也只能读取由ASCII码范围内的一些字符。这些字符主要用于显示现代英语和其他西欧语言。而对于汉字等unicode中的字符则不能正常读取。只能以乱码的形式显示。

对于read()方法的上述缺点,在read(byte[] b)中则得到了解决,就拿汉字来举例,一个汉字占有两个字节,则可以把参数数组b定义为大小为2的数组即可正常读取汉字了。当然b也可以定义为更大,比如如果b=new byte[4]的话,则每次可以读取两个汉字字符了,但是需要注意的是,如果此处定义的大小为37等奇数,则对于全是汉字的一篇文档则不能全部正常读写了。


0 0
原创粉丝点击