IO总体归纳

 IO包括输入和输出2方面内容。在Java设计中IO是什么样的一个架构呢?

 

首先分成2部分,一部分是最基本的字节流,都继承自InputStream/OutputStream,说到底,计算机底层传输的就是字节嘛,不可能是某种特定字符集的字符。那么针对字节流,从哪里来到哪里去,就能够划分好几个种类:比如ByteArrayDataObjectFileSequencePipe。划分好之后,出于性能考虑又加上了Buffer的装饰类来包装具体的字节流类型。到这里,字节流的IO操作差不多就可以满足大多数要求了。

 

这时候,有些人就说了我们平时处理最多的就是文件类型了,你们能不能设计一套针对字符的IO流?OK,没问题,接着Reader/Writer就诞生了,字符就没有字节那么多复杂的种类了,简简单单:CharArrayFilePipe等等,同样在性能考虑上面加入了Buffer来包装具体的字符流。现在大家都满意了,不过等等,问题有出来了,有人说我字符流读进来是乱码,怎么回事?原来是源文件字符集和系统默认字符集不统一,这时候字节流和字符流之间的沟通桥梁InputStreamReader/OutputStreamWriter隆重登场,可以完美解决转换中间的乱码问题。

 

传统的IO整个框架差不多就是上面介绍的了,普通的应用场景,传统的IO已经足够能满足需求了。但是对于一些特殊的应用场景,诸如连接数量非常多,但是时间都不长(典型的就是聊天室了),使用传统的IO的话,数量繁多的线程管理就给整个系统带来了巨大的压力,这时候有人就问了,能不能用一个线程管理所有的链接呢?其实Java1.4版本中间的NIO就能满足类似场景的需求。NIO大体分3块内容,ChannelBufferSelector。我们平时开发就主要和Buffer打交道,内部Buffer会和Channel通信,所以和传统IO相比,NIO是面向缓冲的开发。如果单单只是这样的话,其实还是不能满足先前的要求,这时候通过Channel来设置成非阻塞模式,这样多个Channel之间在一个线程里面就不会相互干扰。最后的Selector其实就是管理多个注册过的Channel,说到底就是一个监听者。不过需要注意的是,NIO中的FileChannel是不能设置成非阻塞模式的。最后需要特别注意的是,把buffer写到Channel之前,需要调用flip()修改buffer为读模式,这时候不能保证buffer是否已经写完,所以要用while做保证。

猜你喜欢

转载自plant12345.iteye.com/blog/2244601