快速业务通道

在Java中使用NIO进行网络编程 - 编程入门网

作者 佚名技术 来源 NET编程 浏览 发布时间 2012-06-17

在Java中使用NIO进行网络编程

时间:2011-04-03 博客园 逖靖寒

在JDK中,有一个非常有意思的库:NIO(New I/O)。这个库中有3个重要的类,分别 是java.nio.channels中Selector和Channel,以及java.nio中的Buffer。

本篇文章我们首先了解一下为什么需要NIO来进行网络编程,然后看看一步一步来讲解 如何在网络编程中使用NIO。

为什么需要NIO

使用Java编写过Socket程序的同学一定都知道Socket和SocketServer。当调用某个调 用的时候,调用的地方就会阻塞,等待响应。这种方式对于小规模的程序非常方便,但是 对于大型的程序就有点力不从心了,当有大量的连接的时候,我们可以为每一个连接建立 一个线程来操作。但是这种做法带来的缺陷也是显而易见的:

1.硬件能够支持大量的并发。

2.并发的数量始终有一个上限。

3.各个线程之间的优先级不好控制。

4.各个Client之间的交互与同步困难。

我们也可以使用一个线程来处理所有的请求,使用不阻塞的IO,轮询查询所有的 Client。这种做法同样也有缺陷:无法迅速响应Client端,同时会消耗大量轮询查询的时 间。

所以,我们需要一种poll的模式来处理这种情况,从大量的网络连接中找出来真正需 要服务的Client。这正是NIO诞生的原因:提供一种Poll的模式,在所有的Client中找到 需要服务的Client。

回到我们刚刚说到的3个最最重要的Class:java.nio.channels中Selector和Channel ,以及java.nio中的Buffer。

Channel 代表一个可以被用于Poll操作的对象(可以是文件流也可以使网络流), Channel能够被注册到一个Selector中。通过调用Selector的 select方法可以从所有的 Channel中找到需要服务的实例(Accept,read ..)。Buffer对象提供读写数据的缓存。 相对于我们熟悉的Stream对象,Buffer提供更好的性能以及更好的编程透明性(人为控制 缓存的大小以及具体的操作)。

配合Buffer使用Channel

与传统模式的编程不用,Channel不使用Stream,而是Buffer。我们来实现一个简单的 非阻塞Echo Client:

package com.cnblogs.gpcuster; import java.net.InetSocketAddress; import java.net.SocketException; import java.nio.ByteBuffer; import java.nio.channels.SocketChannel; public class TCPEchoClientNonblocking {   public static void main(String args[]) throws Exception {    if ((args.length < 2) || (args.length > 3))//  Testforcorrect#ofargs     throw new IllegalArgumentException(       "Parameter(s): <Server> <Word> [<Port>]");    String server = args[0];// ServernameorIPaddress    // ConvertinputStringtobytesusingthedefaultcharset    byte[] argument = args[1].getBytes();    int servPort = (args.length == 3) ? Integer.parseInt(args[2]) :  7;    // Createchannelandsettononblocking    SocketChannel clntChan = SocketChannel.open();    clntChan.configureBlocking(false);    // Initiateconnectiontoserverandrepeatedlypolluntilcomplete    if (!clntChan.connect(new InetSocketAddress(server, servPort)))  {     while (!clntChan.finishConnect()) {      System.out.print(".");// Dosomethingelse     }    }    ByteBuffer writeBuf = ByteBuffer.wrap(argument);    ByteBuffer readBuf = ByteBuffer.allocate(argument.length);    int totalBytesRcvd = 0;// Totalbytesreceivedsofar    int bytesRcvd;// Bytesreceivedinlastread  

凌众科技专业提供服务器租用、服务器托管、企业邮局、虚拟主机等服务,公司网站:http://www.lingzhong.cn 为了给广大客户了解更多的技术信息,本技术文章收集来源于网络,凌众科技尊重文章作者的版权,如果有涉及你的版权有必要删除你的文章,请和我们联系。以上信息与文章正文是不可分割的一部分,如果您要转载本文章,请保留以上信息,谢谢!

分享到: 更多

Copyright ©1999-2011 厦门凌众科技有限公司 厦门优通互联科技开发有限公司 All rights reserved

地址(ADD):厦门软件园二期望海路63号701E(东南融通旁) 邮编(ZIP):361008

电话:0592-5908028 传真:0592-5908039 咨询信箱:web@lingzhong.cn 咨询OICQ:173723134

《中华人民共和国增值电信业务经营许可证》闽B2-20100024  ICP备案:闽ICP备05037997号