java BIO/NIO
一、BIO
Blocking IO(即阻塞IO);
1. 特点:
a) Socket服务端在监听过程中每次accept到一个客户端的Socket连接,就要处理这个请求,而此时其他连接过来的客户端只能阻塞等待;
b) 多线程处理多个连接,每个线程拥有自己的栈空间并且占用一些 CPU 时间。每个线程遇到外部未准备好的时候,都会阻塞掉。阻塞的结果就是会带来大量的线程上下文切换。且大部分线程上下文切换可能是无意义的。比如假设一个线程监听一个端口,一天只会有几次请求进来,但是该 cpu 不得不为该线程不断做上下文切换尝试,大部分的切换以阻塞告终。
2. 流程:
二、 NIO
Java New IO(即非阻塞IO )
1. 特点:
a) 由一个专门的线程来处理所有的 IO 事件,并负责分发。
b) 事件驱动机制:事件到的时候触发,而不是同步的去监视事件。
c) 线程通讯:线程之间通过 wait,notify 等方式通讯。保证每次上下文切换都是有意义的。减少无谓的进程切换。
2. 示例:
服务器端:
ServerSocketChannel serverSocketChannel = ServerSocketChannel.open();
serverSocketChannel.socket().bind(new InetSocketAddress(9999));
while(true){
SocketChannel socketChannel = serverSocketChannel.accept();
//do something with socketChannel...
}
客户端:
SocketChannel socketChannel = SocketChannel.open();
socketChannel.connect(new InetSocketAddress("http://jenkov.com", 80));
ByteBuffer buf = ByteBuffer.allocate(48);
int bytesRead = socketChannel.read(buf);
String newData = "New String to write to file";
ByteBuffer buf = ByteBuffer.allocate(48);
buf.clear();
buf.put(newData.getBytes());
buf.flip();
while(buf.hasRemaining()) {
channel.write(buf);
}
3. Channels(通道):
重要实现类:
1) FileChannel:从文件中读写数据。
2) DatagramChannel:能通过UDP读写网络中的数据。
3) SocketChannel:能通过TCP读写网络中的数据。
4) ServerSocketChannel:可以监听新进来的TCP连接,像Web服务器那样。对每一个新进来的连接都会创建一个SocketChannel。
重要方法:
Read(buf):从通道中读出数据到buf中;
Write(buf):将buf中的数据写入到通道中;
其中FileChanel提供了Map方法,返回一个MappedByteBuffer对象,代表内存映射文件IO,它可以比常规的基于流或者基于通道的I/O快的多。内存映射文件I/O是通过使文件中的数据出现为 内存数组的内容来完成的。
4. Buffers(缓冲区):
本质上是一块可以写入数据,然后可以从中读取数据的内存。用于和NIO通道进行交互(数据是从通道读入缓冲区,从缓冲区写入到通道中的);
继承关系:
重要属性:
序号 |
名称 |
属性功能 |
说明 |
1 |
capacity |
缓冲区大小 |
缓冲内存区域总的字节大小; |
2 |
limit |
实际数据大小 |
读模式时, limit表示你最多能读到多少数据;写模式下,表示你最多能往Buffer里写多少数据;写模式下,limit等于Buffer的capacity。 |
3 |
position |
当前位置 |
表示当前的位置。初始的position值为0,position最大可为capacity–1; |
重要方法:
序号 |
方法名 |
方法功能 |
说明 |
1 |
Flip |
切换到读模式 |
用于从写模式切换到读模式时调用的一个方法,表示最多能读取到多少内容; 具体实现为: 将position设回0,并将limit设置成之前position的值; |
2 |
rewind |
重读Buffer中的所有数据; |
将position设回0,limit保持不变,仍然表示能从Buffer中读取多少数据; |
3 |
Clear compact |
清空缓冲区 |
limit用于将整个缓冲区全部清空,而compact用于在缓冲区还有部分未读完的数据时,将未读完的数据拷贝到缓冲区最前面,将其余部分全部清空; limit和compact在清除缓冲区时都是修改的指针,使得往缓冲区里面写入数据时能覆盖,并不会真正清空缓冲区里面的内容; |
4 |
Mark reset |
标记 恢复标记 |
mark()方法标记Buffer中的一个特定position。通过调用reset()方法恢复这个position; |
5 |
Equals compareTo |
判断是否相等 比较大小 |
equals相等的条件: 1.有相同的类型(byte、char、int等)。 2.Buffer中剩余的byte、char等的个数相等。 3.Buffer中所有剩余的byte、char等都相同。 compareTo:判断Buffer A小于Buffer B的条件: 1.第一个不相等的元素小于另一个Buffer中对应的元素 。 2.所有元素都相等,但第一个Buffer比另一个先耗尽(第一个Buffer的元素个数比另一个少)。 备注:剩余元素是从 position到limit之间的元素 |
6 |
slice |
缓冲区分片 |
根据现有的缓冲区对象来创建一个子缓冲区,即在现有缓冲区上切出一片来作为一个新的缓冲区,但现有的缓冲区与创建的子缓冲区在底层数组层面上是数据共享的,也就是说,子缓冲区相当于是现有缓冲区的一个视图窗口 |
7 |
asReadOnlyBuffer |
创建只读缓冲区 |
这个方法返回一个与原缓冲区完全相同的缓冲区,并与原缓冲区共享数据,只不过它是只读的。如果原缓冲区的内容发生了变化,只读缓冲区的内容也随之发生变化; |
8 |
allocateDirect |
直接缓冲区 |
给定一个直接字节缓冲区,Java虚拟机将尽最大努 力直接对它执行本机I/O操作。也就是说,它会在每一次调用底层操作系统的本机I/O操作之前(或之后),尝试避免将缓冲区的内容拷贝到一个中间缓冲区中 或者从一个中间缓冲区中拷贝数据。 |
5. Selectors(选择器):
选择器用于监听多个通道的事件(比如:连接打开,数据到达)。因此,单个的线程可以监听多个数据通道。
要使用Selector,得向Selector注册Channel,然后调用它的select()方法,接下来就等待事件就绪并处理事件;
使用事项:
1) 与Selector一起使用时,Channel必须处于非阻塞模式下。这意味着不能将FileChannel与Selector一起使用,因为FileChannel不能切换到非阻塞模式。而套接字通道都可以。
2) 选择器监听的事件集合有:SelectionKey.OP_CONNECT, SelectionKey.OP_ACCEPT, SelectionKey.OP_READ, SelectionKey.OP_WRITE;
3) 从SelectionKey中分离出事件的方法:
int interestSet = selectionKey.interestOps();
boolean isInterestedInAccept=(interestSet & SelectionKey.OP_ACCEPT) == SelectionKey.OP_ACCEPT;
boolean isInterestedInConnect = (interestSet & SelectionKey.OP_CONNECT) == SelectionKey.OP_CONNECT;
boolean isInterestedInRead = (interestSet & SelectionKey.OP_READ) == SelectionKey.OP_READ;
boolean isInterestedInWrite = (interestSet & SelectionKey.OP_WRITE) == SelectionKey.OP_WRITE;
同样SelectionKey中也封装了上面的方法:
selectionKey.isAcceptable();
selectionKey.isConnectable();
selectionKey.isReadable();
selectionKey.isWritable();
使用流程:
java BIO/NIO的更多相关文章
- Java BIO NIO 与 AIO
回顾 上一章我们介绍了操作系统层面的 IO 模型. 阻塞 IO 模型. 非阻塞 IO 模型. IO 复用模型. 信号驱动 IO 模型(用的不多,知道个概念就行). 异步 IO 模型. 并且介绍了 IO ...
- JAVA bio nio aio
[转自]http://qindongliang.iteye.com/blog/2018539 在高性能的IO体系设计中,有几个名词概念常常会使我们感到迷惑不解.具体如下: 序号 问题 1 什么是同步? ...
- java BIO/NIO/AIO 学习
一.了解Unix网络编程5种I/O模型 1.1.阻塞式I/O模型 阻塞I/O(blocking I/O)模型,进程调用recvfrom,其系统调用直到数据报到达且被拷贝到应用进程的缓冲区中或者发生错误 ...
- 3. 彤哥说netty系列之Java BIO NIO AIO进化史
你好,我是彤哥,本篇是netty系列的第三篇. 欢迎来我的公从号彤哥读源码系统地学习源码&架构的知识. 简介 上一章我们介绍了IO的五种模型,实际上Java只支持其中的三种,即BIO/NIO/ ...
- JAVA BIO,NIO,Reactor模式总结
传统同步阻塞I/O(BIO) 在NIO之前编写服务器使用的是同步阻塞I/O(Blocking I/O).下面是一个典型的线程池客服端服务器示例代码,这段代码在连接数急剧上升的情况下,这个服务器代码就会 ...
- java BIO NIO IO
参考 https://www.cnblogs.com/zedosu/p/6666984.html 摘要: 关于BIO和NIO的理解 最近大概看了ZooKeeper和Mina的源码发现都是用Java N ...
- I/O模型系列之三:IO通信模型BIO NIO AIO
一.传统的BIO 网络编程的基本模型是Client/Server模型,也就是两个进程之间进行相互通信,其中服务端提供位置信息(绑定的IP地址和监听端口),客户端通过连接操作向服务端监听的地址发起连接请 ...
- (转)也谈BIO | NIO | AIO (Java版)
原文地址: https://my.oschina.net/bluesky0leon/blog/132361 关于BIO | NIO | AIO的讨论一直存在,有时候也很容易让人混淆,就我的理解,给出一 ...
- Java BIO、NIO、AIO 学习(转)
转自 http://stevex.blog.51cto.com/4300375/1284437 先来个例子理解一下概念,以银行取款为例: 同步 : 自己亲自出马持银行卡到银行取钱(使用同步IO时,Ja ...
随机推荐
- L322
As a nutritionist helping people shed pounds, I often recommend incorporating portion-controlled des ...
- oracle 12c 警告日志位置
Oracle 12c环境下查询,alert日志并不在bdump目录下,看到网上和书上都写着可以通过初始化参数background_dump_dest来查看alter日志路径,还说警告日志文件的缺省位置 ...
- 漫步Java------初识java
一. Java语言概述 语言:是人与人之间用于沟通的一种方式. 例如:中国人与中国人用普通话沟通.而中国人要和英国人交流,就要学习英语. 计算机语言(编程语言): 人与计算机交流的方式.如果人要与计算 ...
- 批注@SuppressWarnings 的作用
J2SE 提供的最后一个批注是 @SuppressWarnings.该批注的作用是给编译器一条指令,告诉它对被批注的代码元素内部的某些警告保持静默. 一点背景:J2SE 5.0 为 Java 语言增加 ...
- Invocation of init method failed; nested exception is java.text.ParseException: '?' can only be specfied for Day-of-Month or Day-of-Week.
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'cronTrigger' ...
- 支付宝异步通知(notify_url)与return_url.
支付宝接口使用文档说明 支付宝异步通知(notify_url)与return_url. 现支付宝的通知有两类. A服务器通知,对应的参数为notify_url,支付宝通知使用POST方式 B页面跳转通 ...
- Python之路PythonThread,第四篇,进程4
python3 进程/线程4 进程间同步互斥方法: from multiprocessing import Lock 创建 进程锁对象 lock = Lock() lock.acquire() 给 ...
- 深度学习环境配置Ubuntu16.04+CUDA8.0+CUDNN5
深度学习从12年开始打响,配置深度学习环境软件一直是一个头疼的问题,如何安装显卡驱动,如何安装CUDA,如何安装CUDNN:Ubuntu官方一直吐槽Nvidia显卡驱动有问题,网上大神也给出了关闭li ...
- Gym101986: Asia Tsukuba Regional Contest(寒假自训第12场)
A .Secret of Chocolate Poles 题意:有黑白两种木块,黑色有1,K两种长度: 白色只有1一种长度,问满足黑白黑...白黑形式,长度为L的组合种类. 思路:直接DP即可. #i ...
- CodeForces - 1101G :(Zero XOR Subset)-less(线性基)
You are given an array a1,a2,…,an of integer numbers. Your task is to divide the array into the maxi ...