JAVA NIO
来源:互联网 发布:淘宝网玩具小马会走 编辑:程序博客网 时间:2024/06/14 12:52
Java 提供了NIO概念,也即是非阻塞IO概念。并引入了对文件和socket的一些封装。本文将详细介绍NIO。
Channel
Channel 本质上实现了对句柄的封装。Linux系统中用一个正式fd来描述文件或者网络套接字的唯一封装。Channel大体的意思也是对fd的封装。
Channel有四种,具体为:
ServerSocketChannel //Socket 服务器版本
SocketChannel //Socket 客户端版本
FileChannel //文件Channel
DatagramChannel //UDP
Buffer
Buffer 为读取Socket或者文件的一块内存。每个基本数据都有对应的Buffer。 但常用的只有ByteBuffer,按字节来读数据。
Buffer的方法需要灵活记忆:
Buffer的三个成员变量position, limit 和Capacity. Capacity为这块Buffer的内存大小。
读模式下postion 为当前读到buffer位置的指针,limit为可读数据。
写模式下postion 为当前写到buffer的位置,limit为capacity.
flip()函数写模式向读模式切换。
rewind()函数为读模式下,重新开始读。
clear() 清空所有数据
compact() 把没读的数据拷贝到buffer的开始。
Mark(), Reset()下一个书签功能,回到书签位置继续读。
FileChannel 实例
读文件并打印到控制台。
public static void testChannel() throws IOException{RandomAccessFile raf = new RandomAccessFile("/home/dumplog.py","r");FileChannel fc = raf.getChannel();ByteBuffer bf =ByteBuffer.allocate(16);int len;while((len=fc.read(bf))!=-1){bf.flip();while(bf.hasRemaining())System.out.print((char)bf.get());bf.clear();}raf.close();fc.close();}
SocketChannel 实例
实例接受客户端数据,并打印出来,然后返回一个数据。为了避免复杂,并没有写客户端程序,大家可以用telnet代替。telnet到这个端口,发送数据来测试。当读到的数据长度或者写的数据长度为-1时,意味着链接断开,需要关闭channel.
import java.io.IOException; import java.net.InetSocketAddress; import java.nio.ByteBuffer; import java.nio.channels.SelectionKey; import java.nio.channels.Selector; import java.nio.channels.ServerSocketChannel; import java.nio.channels.SocketChannel; import java.util.Iterator; public class NIOTest { public static void main(String[] args) throws IOException { Selector select = Selector.open(); ServerSocketChannel listenChannel = ServerSocketChannel.open(); listenChannel.configureBlocking(false); listenChannel.socket().bind(new InetSocketAddress(8080)); listenChannel.socket().setReuseAddress(true); listenChannel.register(select, SelectionKey.OP_ACCEPT); while(true) { select.select(); Iterator<SelectionKey> it = select.selectedKeys().iterator();//select.keys().iterator(); while(it.hasNext()) { SelectionKey key = it.next(); it.remove(); if(key.isAcceptable()) { ServerSocketChannel channel = (ServerSocketChannel) key.channel(); SocketChannel clientChannel = channel.accept(); clientChannel.configureBlocking(false); //clientChannel.write(ByteBuffer.wrap(new String("hello,trender").getBytes())); clientChannel.register(select, SelectionKey.OP_READ); } else if(key.isReadable()) { SocketChannel channel = (SocketChannel) key.channel(); // \u521b\u5efa\u8bfb\u53d6\u7684\u7f13\u51b2\u533a ByteBuffer buffer = ByteBuffer.allocate(1024); try { int num = channel.read(buffer); if(num==-1) { channel.close(); continue; } byte[] data = buffer.array(); String msg = new String(data).trim(); System.out.println("\u670d\u52a1\u7aef\u6536\u5230\u4fe1\u606f\uff1a"+msg); ByteBuffer outBuffer = ByteBuffer.wrap(msg.getBytes()); channel.write(outBuffer); channel.register(select, SelectionKey.OP_WRITE); } catch(Exception e) { System.out.print(e); continue; } } else if (key.isWritable()) { SocketChannel channel = (SocketChannel) key.channel(); try { int len =channel.write(ByteBuffer.wrap(new String("hello trender\n").getBytes())); if(len<0) { channel.close(); continue; } channel.register(select, SelectionKey.OP_READ); }catch(Exception e) { System.out.print(e); } } } } } }
小结
本文只是做了最简单的概述,可以让大家快速了解JAVA NIO,代码中还用到了Selector,其实和unix中select 函数一个道理,并没有深入。
建议从事网络相关开发,还需多看代码,最后把java.nio看代码通读下。
0 0
- Java NIO: NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- NIO--JAVA NIO 入门
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- Java NIO:NIO概述
- openstack中的消息总线
- 寻找一个单向链表的中项,如果存在两个则返回前一个,给出算法描述
- input type="radio" 的用法
- js 设置header,实现跨域访问
- 第8周项目1 数组做数据成员 工资类(2)
- JAVA NIO
- 用对象数组操作长方柱类
- Android——Eclipse编程代码提示
- Effective STL条款17-条款18
- iOS应用程序生命周期(前后台切换,应用的各种状态)详解
- Problem1014
- Struts2框架学习(三) 数据处理
- 文章标题
- PHP urlecode urldecode rawurldecode() rawurldecode 区别