Java输入输出流IO介绍(与NIO比较)
一、Java中流的类型
- 根据流的方向划分:输入流,输出流
- 根据流的传输单位:字节流,字符流
-
根据流的角色划分:节点流,处理流
节点流:直接连接数据源的流
处理流:通过构造方法接收一个节点流,对节点流使用装饰者模式增加更多的功能。
二、字节流和字符流的结合使用
用到“适配器(adapter)”类:InputStreamReader可以把InputStream转换为Reader
OutputStreamWriter可以把OutputStream转换为Writer
三、字节流和字符流的区别
1.字节流读到一个返回一个
2.字节流可以处理所有的数据类型
3.字符流使用字节流读取到一个或多个字节,去编码表查找,返回对应的字符
四、RamdomAccessFile
该类的工作方式类似于把DataInputStream和DataOutputStream组合起来使用,并添加了一些方法。
该类自我独立,直接由Object派生而来
通常一个流只有一个功能,要么读要么写。RamdomAccessFile既可以读文件也可以写文件
五、NIO
NIO主要有三大核心部分:Channel(通道),Buffer(缓冲区), Selector(选择器)。传统IO基于字节流和字符流进行操作,而NIO基于Channel和Buffer(缓冲区)进行操作,数据总是从通道读取到缓冲区中,或者从缓冲区写入到通道中。Selector(选择区)用于监听多个通道的事件(比如:连接打开,数据到达)。因此,单个线程可以监听多个数据通道。
六、通道(channel)
用户数 据源节点和目标节点的连接。在Java nio中负责缓冲区中的数据传输, channel本身不存储数据,因此需要配合缓冲区进行传输,实现java.nio.channels.Channel接口 ,主要实现类有FileChannel、SocketChannel、ServerSocketChannel、DatagramChannel等。
获取通道的方式
java针对支持通道的类提供getChannel()方法 本地IO有 FileInputStream/FileOutputStream RandomAccessFile, 网络IO有 Socket 、ServerSocket 、DatagramSocket
在Java1.7中的NIO.2针对各个通道提供了静态方法open()
在Java1.7中的NIO.2的Files工具类的newByteChannel()
七、缓冲区(buffer)
Buffer是数据的容器,在nio中负责数据的存取,java为不同数据类型提供了相对应的缓冲区类型 如:ByteBuffer、CharBuffer、ShortBuffer、IntBuffer、LongBuffer、FloatBuffer 、DoubleBuffer 等。
Buffer的基本使用 :通过allocate()方法获取缓冲区,put()方法存入数据到缓冲区,get()方法获取缓冲区中的数据
Buffer的核心属性:
capacity:容量,表示缓冲区中最大存储数据的容量,一旦声明不能改变。
limit:界限,表示缓冲区中可以操作数据的大小。(limit后数据不能进行读写)
position:位置,表示缓冲区中正在操作数据的位置
mark: 标记,表示记录当前position的位置,可通过reset()恢复到mark的位置
直接缓冲区与非直接缓冲区
非直接缓冲区:通过allocate()分配缓冲区,缓冲区建立在jvm中。
直接缓冲区:通过allocateDirect()方法创建缓冲区,缓冲区建立在系统物理内存中。
链接: 参考文章.
八、Selector
Selector类是NIO的核心类。Selector能够检测多个注册的通道上是否有事件发送,如果有事件发生,便获取事件然后针对每个事件进行相应的响应处理。这样一来,只是用一个单线程就可以管理多个通道。也就是管理多个连接。这样使得只有在连接真正有读写事件发送时,才会调用函数来进行读写,就大大减少了系统开销,并且不必为每个连接创建一个线程,不用去维护多个线程,并且避免了多线程之间上下文切换导致的开销。
九、NIO和普通IO的区
IO | NIO |
---|---|
面向流 | 面向缓冲区 |
堵塞IO | 非堵塞IO |
– | 选择器 |
Java中的NIO实际上采用的是多路复用IO模型
会有一个线程不断去轮询多个socket的状态,只有当socket真正有读写事件时,才真正调用实际的IO读写操作。
十、IO模型
链接: 参考文章.
本文地址:https://blog.csdn.net/YuanJAnt/article/details/107879797