ServerSocketChannel、SocketChannel、Selector等概念04
java.nio包中的主要类
ServerSocketChannel:ServerSocket的替代类,支持阻塞通信与非阻塞通信。
SocketChannel:Socket的替代类,支持阻塞通信与非阻塞通信。
Selector:为ServerSocketChannel监控接收连接的就绪事件,为SocketChannel监控连接就绪、读就绪或写就绪事件。
SelectionKey:代表ServerSocketChannel及SocketChannel向Selector注册事件的句柄。当一个SelectionKey对象位于Selector对象的Selected-keys集合中时,就表示与这个SelectionKey对象相关的事件发生了。
ServerSocketChannel及SocketChannel都是SelectabletChannel的子类。SelectabletChannel类及其子类都能委托Selector来监控他们可能发生的一些事件。这种委托过程也称为注册事件过程。
ServerSocketChannel向Selector注册接收连接就绪事件:
SelctionKey key = serverSocketChannel.register(selector,SelectionKey.OP_ACCEPT);
SocketChannel可能发生以下3钟事件:
SelectionKey.OP_CONNECT:连接就绪事件
SelectionKey.OP_READ:读就绪事件,表示输入流中已经有了可读数据
SelectionKey.OP_WRITE:写就绪事件,表示已经可以向输出流写数据了。
SocketChannel提供了接收和发送数据的方法
read(ByteBuffer buffer):接收数据,把他们存放到参数指定的ByteBuffer中。
write(ByteBuffer buffer):把参数指定的ByteBuffer中的数据发送出去。
ByteBuffer表示字节缓冲区,ByteBuffer继承于Buffer类。ByteBuffer存放字节,为了把他们转换为字符串,还需要用到Charset类,Charset类代表字符编码,它提供了把字节流转换为字符串(解码过程)和把字符串转换为字节流(编码过程)的实用方法。
-----
Charset类提供了编码与解码方法:
ByteBuffer encode(String str):对参数str指定的字符串进行编码,把得到的字节序列存放在一个ByteBuffer对象中,并将其返回。
ByteBuffer encode(CharBuffr cb):字符到字节(编码)
CharBuffer decode(ByteBuffer bb):字节到字符(解码)
Charset类的静态forName(String encode)方法返回一个Charset对象,
Charset charset = Charset.forName("GBK");
--------
ServerSocketChannel类
ServerSocketChannel ssc = ServerSocketChannel.open();
这个方法没有与任何本地端口绑定,并且处于阻塞模式;
SocketChannel sc = ssc.accept();用于接收客户连接,如果ServerSocketChannel处于非阻塞模式,当没有客户连接时,该方法立即返回null.返回的SocketChannel是阻塞的,要设置非阻塞需要socketChannel.configureBlocking(false);[p/95页详细信息】
-------
Selector类:
只要ServerSocketChannel及SocketChannel向Selector注册了特定的事件,Selector就会监控这些事件是否发送。SelectableChannel的register()方法负责注册事件,该方法返回一个SelectionKey对象,该对象是用于跟踪这些注册事件的句柄。一个Selector对象中会包含3中类型的SelectionKey集合。
1、all-keys集合:当前所有想Selector注册的SelectionKey集合,Selector的keys方法返回该集合。
2、selected-key集合:相关事件已经被Selector捕获的SelectionKey的集合。Selector的selectedKeys()方法返回该集合。
3、cancelled-keys集合:已经被取消的SelectionKey的结合。Selector没有提供访问这种集合的方法。
当执行SelectableChannel的register()方法时,该方法新建一个SelectionKey,并把它加入Selector的all-keys集合中。
如果关闭了与SelectionKey对象关联的Channel对象,或者调用了SelectionKey对象的cancel()方法,这个SelectionKey对象就会被加入cancelled-keys集合中,表示这个SelectionKey对象已经被取消,在程序下一次执行的Seelector的select()方法时,被取消的SelectionKey对象将从所有的集合中删除。
在执行Selector的select()方法时,如果与SelecitonKey相关的事件发生了,这个SeletionKey就被加入到selected-keys集合中。程序直接调用selected-keys集合的remove()方法,或者调用它的Itertor的remove()方法,都可以从selected-keys集合中删除一个SelectionKey对象。
Selector主要的方法:
public static Selector open();创建一个Selector对象;
public boolean isOpen();Selector对象创建好了就处于打开状态
public Set<SelectionKey> keys()返回Selector的all-keys集合,它包含了所有与Selector关联的SelectiOnKey对象。
public int selectNow();返回相关事件已经发生的SelectionKey对象的数目。
public int select();
public Selector wakeup();唤醒执行Seletor的方法的线程。
------------
SelctionKey类
SeverSocketChannel或Socket类通过register()方法向Selector注册事件时,register()方法会创建一个SelectionKey对象,这个SelectionKey对象是用来跟踪注册事件的句柄。在SelectionKey对象的有效时间,Selector会一直监控与SelectionKey对象相关的事件,如果事件发生,就会把SelectionKey对象加入seleected-keys集合中。以下情况下SelectionKey对象会失效。
1、程序调用了SelectionKey的cancel()方法。
2、关闭与SelectionKey关联的Channel
3、与SelectionKey的Selector被关闭。
在SelectionKey中定义了4中事件:
SelecitonKey.OP_ACCEPT:接收连接就绪事件,表示服务器监听到了客户连接,服务器可以接收这个链接了。常量值为16。
SelectionKey.OP_CONNECT:连接就绪事件,表示客户与服务器的连接已经建成功了。常量值为8.
SelectionKey.OP_READ:读就绪事件,表示通道中已经有了可读数据,可以执行读操作了。常量值为1.
SelecitonKey.OP_WRITE:写就绪事件,表示已经可以向通道写数据了。常量值为4.
返回值为SelecitonKey.OP_WRITE|SelectionKey.OP_READ就表示这个SelectionKey对读就绪和写就绪事件感兴趣。与之关联的Selector对象会负责监控这些事件。当通过SelectableChannel的register()方法注册事件时,可以在参数中指定SelectionKey感兴趣的事件。
SelectionKey = key socketChannel.register(selector,SelecitonKey.OP_WRITE|SelectionKey.OP_READ);
SelecitonKey的interestOps(int ops)方法用于为SelectionKey对象增加一个感兴趣的事件。
key.interestOps(SelecitonKey.OP_WRITE);
所有已经发生的事件:SelectionKey的readyOps()方法返回所有已经发生的事件。例如,假如返回值为SelecitonKey.OP_WRITE|SelectionKey.OP_READ。表示读就绪和写就绪事件已经发生了,这就意味着与之关联的SocketChannel对象可以进行读操作和写操作了。
当程序调用了一个SelectableChannel的register(selector,xxx)方法,该方法建立了SelectableChannel对象、Selector对象以及register()方法所创建的SelecitonKey对象之间的管理关系。
SelectionKey主要方法:
public SelectableChannel channel():返回与这个SelectionKey对象关联的SelectableChannel对象。
public Selector selector():返回与这个SelectionKey对象关联的Selector对象。
public boolean isValid()判断这个SelectionKey是否有效。
public void cancel();使这个SelectionKey对象失效。
public int interestOps()返回这个SelectionKey感兴趣的事件。
public int interestOps(int ops),增加感兴趣事件
public int readyOps():返回已经就绪的事件
public final boolean isReadable();判断与之关联的SocketChannel的读就绪事件是否已经发生。该方法等价于:key.readyOps()&&OP_READ !=0
public final boolean isWritable()
public final boolean isConnectAble();
public final boolean isAcceptable();
public final Object attach(Object obj)使SelecitonKey关联一个附件。
public final Object attachment():返回SelecitonKey对象关联的附件。
ServerSocketChannel、SocketChannel、Selector等概念04的更多相关文章
- Java 阻塞
对于用ServerSocket 及 Socket 编写的服务器程序和客户程序, 他们在运行过程中常常会阻塞. 例如, 当一个线程执行 ServerSocket 的accept() 方法时, 假如没有客 ...
- javaAPI1
Iterable<T>接口, Iterator<T> iterator() Collection<E>:接口,add(E e) ,size() , Object[] ...
- java的nio之:java的nio系列教程之selector
一:Java NIO的selector的概述===>Selector(选择器)是Java NIO中能够检测一到多个NIO通道,并能够知晓通道是否为诸如读写事件做好准备的组件.这样,一个单独的线程 ...
- NIO组件Selector详解
Selector(选择器)是Java NIO中能够检测一到多个NIO通道,并能够知晓通道是否为诸如读写事件做好准备的组件.这样,一个单独的线程可以管理多个channel,从而管理多个网络连接. 下面是 ...
- Selector 实现原理
概述 Selector是NIO中实现I/O多路复用的关键类.Selector实现了通过一个线程管理多个Channel,从而管理多个网络连接的目的. Channel代表这一个网络连接通道,我们可以将Ch ...
- 7. 彤哥说netty系列之Java NIO核心组件之Selector
--日拱一卒,不期而至! 你好,我是彤哥,本篇是netty系列的第七篇. 简介 上一章我们一起学习了Java NIO的核心组件Buffer,它通常跟Channel一起使用,但是它们在网络IO中又该如何 ...
- (四:NIO系列) Java NIO Selector
出处:Java NIO Selector 1.1. Selector入门 1.1.1. Selector的和Channel的关系 Java NIO的核心组件包括: (1)Channel(通道) (2) ...
- Java NIO Selector 的使用
之前的文章已经把 Java 中 NIO 的 Buffer.Channel 讲解完了,不太了解的可以先回过头去看看.这篇文章我们就来聊聊 Selector -- 选择器. 首先 Selector 是用来 ...
- NIO的Selector
参考自 Java NIO系列教程(六) Selector Java-NIO-Selector java.nio.channels.Selector NIO新功能Top 10(下) 出发点: 如何管理多 ...
随机推荐
- ARP欺骗攻击
一.ARP攻击概述 ARP攻击主要是存在于局域网中,通过伪造IP地址和MAC地址实现ARP欺骗,能够在网络中产生大量的ARP通信量使网络阻塞,攻击者只要持续不断的发出伪造的ARP响应包就能更改目标主机 ...
- 一文带你看透kubernetes 容器编排系统
本文由云+社区发表 作者:turboxu Kubernetes作为容器编排生态圈中重要一员,是Google大规模容器管理系统borg的开源版本实现,吸收借鉴了google过去十年间在生产环境上所学到的 ...
- GitHub 开源的 MySQL 在线更改 Schema 工具【转】
本文来自:https://segmentfault.com/a/1190000006158503 原文:gh-ost: GitHub's online schema migration tool fo ...
- MVC+angularjs
angularjs可以解决开发人员不擅长HTML的问题,采用模块化配置,但是不支持样式的微调和修改 angularjs+MVC开发的协同办公平台,贴下图 编辑页面+附件 列表页 一个页面涉及另一个子表 ...
- 《Web安全深度剖析》
书名 <Web安全深度剖析> 图片 时间 2018-11月 总结 算是我安全的启蒙书 前五章都是工具 看完差不多算个脚本小子 后面的实战感觉很空洞没什么实战
- Java开发笔记(十七)各得其所的多路分支
前面提到条件语句的标准格式为“if (条件) { /* 条件成立时的操作代码 */ } else { /* 条件不成立时的操作代码 */ }”,乍看之下仿佛只有两个分支,一个是条件成立时的分支,另一个 ...
- TypeScript,初次见面,请多指教 ?
为什么用 TS ? 说实话,最开始并没有想把 TS 用到实际项目中来,一来是感觉"类型"会限制 JS 的优势(好吧,就是浪写浪惯了):二来听闻 TS + Redux 的酸爽滋味,有 ...
- 详解Vue Native
译者按: 一家叫GeekyAnts的印度公司开发了Vue Native,基于React Native实现. 原文: Introducing Vue Native 译者: Fundebug 为了保证可读 ...
- centos7 Failed to start firewalld.service: Unit is masked.
centos7 启动防火墙失败:Failed to start firewalld.service: Unit is masked. ---- 刚yum安装了iptables 解决: 执行”sys ...
- vue 音乐App QQ音乐搜索列表最新接口跨域设置
在 webpack.dev.config.js中 'use strict' const utils = require('./utils') const webpack = require('webp ...