NIO网络编程之Selector介绍

Selector

要实现异步IO要通过Selector,甚至我们可以通过一个线程管理多个Channel的读写,这是NIO相较BIO的优越之处之一。

Channel可以注册到一个Selector上,Selector可以监视多个Channel的状态

Channel的状态有四种:

  • CONNECT
  • ACCEPT
  • READ
  • WRITE

CONNECT代表某个Channel成功连接到另一个服务器(客户端)。ACCEPT则是一个ServerSocketChannel准备好接收新连接(服务端)。READ代表该Channel有数据可读,WRITE代表该Channel等待写操作。

这些状态在Java中对应SelectionKey中的四个常量

  • SelectionKey.OP_CONNECT
  • SelectionKey.OP_ACCEPT
  • SelectionKey.OP_READ
  • SelectionKey.OP_WRITE

在给Channel注册到Selector时可以指定要监听的状态:

channel.configureBlocking(false);
SelectionKey key =channel.register(selector,SelectionKey.OP_READ);

这个状态可以是多个状态合成的,我们叫它interestOps,是任意几个状态的位或结果。

register方法可以返回一个SelectionKey,作为注册在该Selector上的Channel的唯一标识(一个Selector-Channel对)。

Selector的常用API:

  • int select():阻塞等待,直到至少有一个绑定的Channel符合监听的状态,返回符合状态Channel的个数,也可能是0(如果中途有一个Key的interestOps被更新了)。
  • int select(long timeout) :阻塞等待限制一个最长时间,超过时间直接返回。
  • int selectNow():不阻塞,直接查询有几个符合监听状态的Channel。
  • Set<SelectionKey> selectedKeys():经过任一select操作后可以获取被select到的keys。
  • Selector wakeup():如果一个线程调用select()方法阻塞了,可以让另一个线程调用同一个Selector上的wakeup()方法来唤醒这个线程。
  • void close():关闭这个Selector。

SelectionKey

SelectionKey的常用API:

  • int interestOps():返回interestOps,可以通过与常量进行位与来判断是否含有某个状态。
  • int readyOps():返回的是有哪些监听的状态目前是对应的,也是合成值,可以通过与常量进行位与来判断是否含有某个状态。或者直接调用isConnectable,isAcceptable,isReadable,isWritable
  • SelectableChannel channel():获取这个SelectionKey对应的Channel
  • Selector selector(): 获取这个SelectionKey对应的Selector
  • Object attach(Object ob):给这个SelectionKey附加一个Object对象
  • Object attachment():获取这个附加的Object对象

原创文章,作者:彭晨涛,如若转载,请注明出处:https://www.codetool.top/article/nio%e7%bd%91%e7%bb%9c%e7%bc%96%e7%a8%8b%e4%b9%8bselector%e4%bb%8b%e7%bb%8d/

(0)
彭晨涛彭晨涛管理者
上一篇 2020年2月7日
下一篇 2020年2月7日

相关推荐

  • ArrayList源码分析

    总结 总结放前面防止太长不看: ArrayList内部是用数组实现的。 如果使用无参构造函数建立ArrayList,在添加第一个元素的时候会分配10个元素的空间。 ArrayLis…

    2019年11月22日
    0160
  • AbstractCollection默认集合类

    AbstractCollection用于实现基本的Collection结构,提供给普通用户继承使用。也是JDK集合类的父类,部分方法是没有被重载的。 相比Collection接口并…

    Java 2019年11月18日
    0100
  • 深入理解java虚拟机第三版读书笔记09

    续深入理解java虚拟机第三版读书笔记08 类加载器 通过一个类的全限定名来获取描述该类的二进制字节流称为类加载器。类加载器可以用户自定义,是java语言流行的一项原因 类与类加载…

    2020年1月23日
    0130
  • HashMap源码分析

    HashMap是java中非常常见的一个数据结构,在这篇文章里,我依然以Map中的操作为导向来循序渐进研究HashMap中的源码,阅读这篇文章需要的前置知识有: 弱平衡的二叉查找树…

    Java 2020年2月12日
    0230
  • Java基础查缺补漏05

    继续我的复习刷题 可以有和类名同名的函数 题目: JAVA中,下列语句哪一个正确() A. class中的constructor不可省略B. constructor必须与class…

    Java 2020年5月29日
    0140
  • HashSet源码分析

    Set家族一览: HashSet简介 Set是Collection三大接口其中之一,意为集合,且元素不能重复。Set接口中的方法和Collection中的方法完全一致,只是起到一个…

    2019年12月2日
    0200
  • Java多线程共享模型之管程

    Monitor(锁) Monitor被翻译为监视器或管程。 Monitor是重量级锁的实现,是向操作系统申请的。 Monitor的结构:WaitSet、EntryList、Owne…

    2020年2月2日
    0930
  • Java中的File类以及IO流

    File 类 概述 java.io.File 类是文件和目录路径名的抽象表示,主要用于文件和目录的创建、查找和删除等操作。 构造方法 public File(String path…

    Java 2020年2月4日
    0150
  • 详解java中的unicode编码(码点)

    致谢: 本文参考网页:Unicode字符集以及UTF-8,UTF-16编码的总结 - vcj1009784814的博客 - CSDN博客 Unicode unicode的码点从U+…

    2019年11月25日
    0890
  • Java基础查缺补漏04

    继续我的复习刷题 接口方法可以使用abstract修饰 问题: java接口的方法修饰符可以为?(忽略内部接口) A. privateB. protectedC. finalD. …

    Java 2020年5月28日
    0200

发表回复

登录后才能评论