博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Java NIO 学习:通道(Channel)
阅读量:6073 次
发布时间:2019-06-20

本文共 2663 字,大约阅读时间需要 8 分钟。

hot3.png

  通道(Channel)用于在字节缓冲区(通道只能在字节缓冲区上操作)和位于通道另一侧的实体(通常是一个文件或套接字)之间有效地传输数据,并且通道往往是和操作系统的文件描述符(File Descriptor)和文件句柄(File Handle)对应的,可以用最小的总开销来访问操作系统本身的I/O服务

通道基础

  如下所示

140733_LVVN_1169289.gif

  基本的Channel接口源码

package java.nio.channels; public interface Channel { public boolean isOpen( );  //通道是否打开 public void close( ) throws IOException; //关闭一个打开的通道}

  InterruptibleChannel是一个标记接口,标示该通道是可以中断的(Interruptible),如果连接可中断通道的线程被中断,那么该通道会以特别的方式工作。大多数但非全部的通道都是可以中断的

  类层次结构中有两个类位于一个不同的包:java.nio.channels.spi。这两个类AbstractInterruptibleChannelAbstractSelectableChannel,它们分别为可中断的(interruptible)和可选择的(selectable)的通道实现提供所需的常用方法

打开通道

  IO可以分为File I/O和Stream I/O,通道也可以分为文件(file)通道和套接字(socket)通道,最常用的分别是FileChannel类和三个socket通道类:SocketChannelServerSocketChannelDatagramChannel

  Socket通道有可以直接创建新socket通道的工厂方法。但是一个FileChannel对象却只能通过在一个打开的RandomAccessFile、FileInputStream或FileOutputStream对象上调用getChannel( )方法来获取

package com.henrysun.javaSE.niostudy;import java.io.IOException;import java.io.RandomAccessFile;import java.net.InetSocketAddress;import java.nio.channels.DatagramChannel;import java.nio.channels.FileChannel;import java.nio.channels.ServerSocketChannel;import java.nio.channels.SocketChannel;/** * 打开通道 */public class ChannelOpen {	/**	 * @param args	 * @throws IOException 	 */	public static void main(String[] args) throws IOException {		SocketChannel sc = SocketChannel.open();		sc.connect(new InetSocketAddress("somehost", 8080));		ServerSocketChannel ssc = ServerSocketChannel.open();		ssc.socket().bind(new InetSocketAddress(8090));		DatagramChannel dc = DatagramChannel.open();		RandomAccessFile raf = new RandomAccessFile("somefile", "r");		FileChannel fc = raf.getChannel();	}}

使用通道

  上面的类图结构,大部分零乱部分移除可以得到如下的UML图

193711_LIEn_1169289.png

public interface ReadableByteChannel extends Channel {	public int read(ByteBuffer dst) throws IOException;}public interface WritableByteChannel extends Channel {	public int write(ByteBuffer src) throws IOException;}public interface ByteChannel extends ReadableByteChannel, WritableByteChannel {}

  通道可以是单向的或者双向的,一个channel类可能实现定义read( )方法的ReadableByteChannel接口,而另一个channel类也许实现WritableByteChannel接口以提供write( )方法。实现这两种接口其中之一的类都只能在一个方向上传输数据。如果一个类同时实现这两个接口,那么它可以双向传输数据。这对于sockets不是问题,因为它一直是双向的,但是从FileInputStream对象的getChannel( )方法获取的FileChannel对象是只读的,因为FileInputStream对象总是以read-only的权限打开文件,尽管FileChannel实现了ByteChannel接口。调用write( )方法将抛出未经检查的NonWritableChannelException异常

  通道可以以阻塞和非阻塞模式运行。非阻塞模式的通道永远不会让调用的线程休眠。请求的操作要么立即完成,要么返回一个结果表明未进行任何操作。只有面向流的(stream-oriented)的通道,如sockets和pipes才能使用非阻塞模式

  :socket通道类从SelectableChannel引申而来。从SelectableChannel引申而来的类可以和支持有条件的选择(readiness selectio)的选择器(Selectors)一起使用。将非阻塞I/O和选择器组合起来可以使您的程序利用多路复用I/O(multiplexed I/O)

 

转载于:https://my.oschina.net/HerrySun/blog/737165

你可能感兴趣的文章
网思科技校园网计费解决方案
查看>>
我的友情链接
查看>>
携程 Apollo分布式部署
查看>>
2017 Hackatari Codeathon B. 2Trees(深搜)(想法)
查看>>
单词统计
查看>>
输入一个数字计算圆的面积
查看>>
在Delphi中隐藏程序进程
查看>>
AngularJS PhoneCat代码分析
查看>>
maven错误解决:编码GBK的不可映射字符
查看>>
2016/4/19 反射
查看>>
SharePoint Wiki发布页面的“保存冲突”
查看>>
oracle 10g 数据库与客户端冲突导致实例创建无监听问题
查看>>
Delphi中读取文本文件的方法(实例一)
查看>>
Linux常用命令
查看>>
Android开源代码解读の使用TelephonyManager获取移动网络信息
查看>>
想说一点东西。。。。
查看>>
css知多少(8)——float上篇
查看>>
NLB网路负载均衡管理器详解
查看>>
水平添加滚动条
查看>>
PHP中”单例模式“实例讲解
查看>>