Java网络编程 (5).doc_第1页
Java网络编程 (5).doc_第2页
Java网络编程 (5).doc_第3页
Java网络编程 (5).doc_第4页
Java网络编程 (5).doc_第5页
已阅读5页,还剩2页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

Java网络编程 (5) 作者:刘晓华 发文时间:2004.11.22使用Java NIO提高服务端程序的性能 在前面的章节里,我们讨论了Java NIO的基本概念,在这一节里,我们将结合具体的Java Socket编程,讨论使用NIO提高服务端程序的性能的问题。 Java NIO增加了新的SocketChannel、ServerSocketChannel等类来提供对构建高性能的服务端程序的支持。SocketChannel、ServerSocketChannel能够在非阻塞的模式下工作,它们都是selectable的类。在构建服务器或者中间件时,推荐使用Java NIO。 在传统的网络编程中,我们通常使用一个专用线程(Thread)来处理一个Socket连接,通过使用NIO,一个或者很少几个Socket线程就可以处理成千上万个活动的Socket连接。 通常情况下,通过ServerSocketChannel.open()获得一个ServerSocketChannel的实例,通过SocketChannel.open或者serverSocketChannel.accept()获得一个SocketChannel实例。要使ServerSocketChannel或者SocketChannel在非阻塞的模式下操作,可以调用serverSocketChannel.configureBlocking (false);或者socketChannel.configureBlocking (false); 语句来达到目的。通常情况下,服务端可以使用非阻塞的ServerSocketChannel,这样,服务端的程序就可以更容易地同时处理多个socket线程。 下面我们来看一个综合例子,这个例子使用了ServerSocketChannel、SocketChannel开发了一个非阻塞的、能处理多线程的Echo服务端程序,见示例12-14。【程序源代码】 1/ = Program Discription =2/ 程序名称:示例12-14 : SocketChannelDemo.java3/ 程序目的:学习Java NIO#SocketChannel4/ =567import java.nio.ByteBuffer;8import java.nio.channels.ServerSocketChannel;9import java.nio.channels.SocketChannel;10import java.nio.channels.Selector;11import java.nio.channels.SelectionKey;12import java.nio.channels.SelectableChannel;1314import .Socket;15import .ServerSocket;16import .InetSocketAddress;17import java.util.Iterator;1819public class SocketChannelDemo 202122public static int PORT_NUMBER = 23;/监听端口23ServerSocketChannel serverChannel;24ServerSocket serverSocket ;25Selector selector ;26private ByteBuffer buffer = ByteBuffer.allocateDirect (1024);2728public static void main (String args)29throws Exception3031SocketChannelDemo server=new SocketChannelDemo();32server.init(args);33server.startWork();34353637public void init (String argv)throws Exception3839int port = PORT_NUMBER;4041if (argv.length 0) 42port = Integer.parseInt (argv 0);434445System.out.println (Listening on port + port);4647/ 分配一个ServerSocketChannel48serverChannel = ServerSocketChannel.open();49/ 从ServerSocketChannel里获得一个对应的Socket50serverSocket = serverChannel.socket();51/ 生成一个Selector52selector = Selector.open();5354/ 把Socket绑定到端口上55serverSocket.bind (new InetSocketAddress (port);56/serverChannel为非bolck57serverChannel.configureBlocking (false);5859/ 通过Selector注册ServerSocetChannel60serverChannel.register (selector, SelectionKey.OP_ACCEPT);61626364 public void startWork()throws Exception 6566 67 while (true) 6869int n = selector.select();/获得IO准备就绪的channel数量7071if (n = 0) 72continue;/ 没有channel准备就绪,继续执行737475/ 用一个iterator返回Selector的selectedkeys76Iterator it = selector.selectedKeys().iterator();7778/ 处理每一个SelectionKey79while (it.hasNext() 80SelectionKey key = (SelectionKey) it.next();8182/ 判断是否有新的连接到达83if (key.isAcceptable() 84/返回SelectionKey的ServerSocketChannel85ServerSocketChannel server =(ServerSocketChannel) key.channel();86SocketChannel channel = server.accept();8788registerChannel (selector, channel,89SelectionKey.OP_READ);9091doWork (channel);929394/ 判断是否有数据在此channel里需要读取95if (key.isReadable() 96 97processData (key);9899100101/删除 selectedkeys102it.remove();103104105106protected void registerChannel (Selector selector,107SelectableChannel channel, int ops)108throws Exception109 110if (channel = null) 111return;112113114115channel.configureBlocking (false);116117channel.register (selector, ops);118119120 /处理接收的数据121protected void processData (SelectionKey key)122throws Exception123124125126SocketChannel socketChannel = (SocketChannel) key.channel();127int count;128129buffer.clear();/ 清空buffer130131/ 读取所有的数据132while (count = socketChannel.read (buffer) 0) 133buffer.flip();134135/ send the data, dont assume it goes all at once136while (buffer.hasRemaining()137138/如果收到回车键,则在返回的字符前增加echo$字样139if(buffer.get()=(char)13)140141buffer.clear();142buffer.put(echo$.getBytes();143buffer.flip();144145146socketChannel.write (buffer);/在Socket里写数据147148149buffer.clear();/ 清空buffer150151152if (count 0) 153/ count0,说明已经读取完毕154socketChannel.close(); 155156157158159private void doWork (SocketChannel channel)throws Exception160161buffer.clear();162buffer.put (Hello,I am working,please input some thing,and i will echo to you!rnecho $.getBytes();163buffer.flip();164channel.write (buffer);165166167使用:运行此程序,然后在控制台输入命令telnet localhost 23。 【程序输出结果】如图12-1所示。 图12-1 输出结果【程序注解】关于程序的解释已经包含在程序里面了,在这里我们总结以下使用ServerSocket Channel开发服务端程序的过程:(1)分配一个ServerSocketChannel。(2)从ServerSocketChannel里获得一个对应的ServerSocket。(3)生成一个Selector实例。(4)把ServerSocket绑定到端口上。(5)设置ServerSocketChannel为非block模式(可选)。(6)在Selector里注册ServerSocetChannel。(7)用一个无限循环语句始终查看Selector里是否有IO准备就绪的channel。如果有,就执行对应的处理,如果没有,继续循环。 小 结 在本章我们主要介绍了Java中的网络编程。Java一开始就是一种网络编程语言,到后来才应用到各个方面,所以在Java中进行网络编程远比在C/C+中方便。 我们介绍了几个在网络编程中很重要的类,如InetAddress、URL、URLConnection、Socket、ServerSo

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论