java NIO selector
所属分类 nio
浏览量 1479
A multiplexor of SelectableChannel objects.
Selector 多路复用 SelectableChannel对象, 识别通道是否发生感兴趣的事件 譬如读写事件
// 1.创建Selector
Selector selector = Selector.open();
// 2.将Channel注册到选择器中
// 注册到Selector上的 Channel 必须是非阻塞的,FileChannel 是阻塞的,不可以注册到Selector
channel.configureBlocking(false);
// 第二个参数指定 感兴趣事件
// 可使用或运算| 组合多个事件 SelectionKey.OP_READ | SelectionKey.OP_WRITE
SelectionKey key = channel.register(selector , SelectionKey.OP_READ);
// 一个 Channel 仅仅可以被注册到一个 Selector 一次, 如果将 Channel 注册到 Selector 多次, 相当于更新 SelectionKey 的 interest set.
SelectionKey 类型
OP_READ 可读事件 1<<0 1
OP_WRITE 可写事件 1<<2 4
OP_CONNECT 客户端连接服务端的事件(tcp连接) 1<<3 8
OP_ACCEPT 服务端接收客户端连接的事件 1<<4 16
一个Selector内部维护了三组keys
key set:当前channel注册在Selector上所有的key 可调用keys()获取
selected-key set:当前channel就绪的事件 可调用selectedKeys()获取
cancelled-key:主动触发SelectionKey#cancel()方法会放在该集合,前提条件是该channel没有被取消注册 不可通过外部方法调用
Selector类方法
open():创建一个Selector对象
isOpen():是否是open状态,如果调用了close()方法则返回false
provider():获取当前Selector的Provider
Selector的具体实现
openjdk SelectorImpl
linux2.6以后 EpollSelectorImpl
Windows平台 WindowsSelectorImpl
MacOSX平台 KQueueSelectorImpl
keys() 获取当前channel注册在Selector上所有的key
selectedKeys():获取当前channel就绪的事件列表
selectNow():获取当前是否有事件就绪,立即返回结果,不会阻塞;如果返回值>0,则代表存在一个或多个
select(long timeout): 带超时的阻塞方法 ,超时后直接返回
select(): 阻塞方法,直到有事件就绪才会返回
wakeup():调用该方法,阻塞在select()上的线程立马返回
close(): 关闭Selector,使注册到该Selector上的所有SelectionKey实例无效。channel本身不会关闭。
往Channel注册Selector会返回一个SelectionKey对象 ,包含如下信息
interest set,当前Channel感兴趣的事件集
ready set
channel
selector
attached object,可选的附加对象
// 返回当前感兴趣的事件列表
int interestSet = key.interestOps();
// 可通过interestSet判断其中包含的事件
boolean isInterestedInAccept = interestSet & SelectionKey.OP_ACCEPT;
boolean isInterestedInConnect = interestSet & SelectionKey.OP_CONNECT;
boolean isInterestedInRead = interestSet & SelectionKey.OP_READ;
boolean isInterestedInWrite = interestSet & SelectionKey.OP_WRITE;
// 可通过interestOps(int ops)方法修改事件列表
key.interestOps(interestSet | SelectionKey.OP_WRITE);
ready set
当前Channel就绪的事件列表
int readySet = key.readyOps();
key.isReadable(); //读事件是否就绪
key.isWritable(); //写事件是否就绪
key.isConnectable(); //客户端连接事件是否就绪
key.isAcceptable(); //服务端连接事件是否就绪
channel和selector
通过SelectionKey来获取当前的channel和selector
// 返回当前事件关联的通道, ServerSocketChannel SocketChannel
Channel channel = key.channel();
// 返回当前事件所关联的Selector对象
Selector selector = key.selector();
attached object
可在selectionKey中附加一个对象
key.attach(theObject);
Object attachedObj = key.attachment();
在注册时直接附加
SelectionKey key = channel.register(selector, SelectionKey.OP_READ, theObject);
上一篇
下一篇
netty高性能之道
PooledByteBufAllocator跟踪调试
netty代码debug切入点
缓存雪崩穿透预热更新降级
服务器性能指标介绍
spring资源Resource接口