`
adapterofcoms
  • 浏览: 74645 次
  • 性别: Icon_minigender_1
  • 来自: 苏州
社区版块
存档分类
最新评论

java nio在多线程环境下的恶梦之终结

阅读更多

有人说java nio在多线程环境下编程简直就是个恶梦,其实你如果能把握住java nio API的要领,你就可以将之驾驭.

 

0. 一个 channal 对应一个SelectionKey in the same selector.

e.g:

SelectionKey sk=sc.register(selector, SelectionKey.OP_READ, handler);

sk==sc.register(selector, SelectionKey.OP_WRITE, handler) true?

 

selector.select() 每次返回的对同一channal的sk是否相同?

 

1.channel.register(...) may block if invoked concurrently with another registration[another.register(...)] or selection operation[selector.select(...)] involving *****the same selector*****.

这个是register方法jdk src上的原文,

e.g:

如果一个selection thread已经在select方法上等待ing,那么这个时候如果有另一条线程调用channal.register方法的话,那么它将被blocking.

 

2.selectionKey.cancel() : The key will be removed from all of the selector's key sets during *****the next selection operation[selector.select(...)]*****.
may block briefly if invoked concurrently with a cancellation[cancel()] or selection operation[select(...)] involving ***the same selector***.

这个也是cancel方法jdk src上的原文,

e.g:

你先将一个selectionKey.cancel(),然后随即再channel.register to the same selector,
在cancel和register之间,如果没有线程(包括当前线程)进行select操作的话,

那么 throws java.nio.channels.CancelledKeyException.
所以 cancel-->select-->re-register. 

 

3.if don't remove the current selectedKey from selector.selectedKeys()[Set] 将导致 selector.select(...) not block [may be cpu 100%,specially when client cut the current channel(connection)].

e.g:

Iterator<SelectionKey> it=selector.selectedKeys().iterator();

...for/while it.hasNext()...
it.remove();<------*****must do it. or Keys' Set.clear() finally;

 

if remove the current selectedKey from selector.selectedKeys()[Set] but don't sk.interestOps(sk.interestOps()& (~sk.readyOps()));将导致 selector.select(...) not block [select() not block several times, or excepted exception]

 

4.op_write should not be registered to the selector.   [may be cpu100%]

 

5. if involving  wakeup() before select() [wakeup called several times >=1],the next select() not block [not block just once].

 

尽管以前有些人分析了nio的wakeup性能及not block in linux的bug,但是java nio依然是高效的,那些c/c++的牛人们应该去关注一下jre/bin目录下的nio.dll[windows上的jdk1.6还没有使用IOCP] , ./jdk/jre/lib/amd64/libnio.so[linux上的jdk1.6已经使用epoll了].

基于java nio的服务器:mina,xSocket,girzzly[glassfish],jetty(基于girzzly),tomcat6[可以配置Http11NioProtocol]...其中从本人对girzzly,tomcat6的源码分析来看,它们都还没有真正发挥出nio异步处理请求的优点,它们的读写还都是blocking的虽然使用了selectorPool,此外tomcat6要剥离出socket通信还要花费一定的功夫.而mina,xSocket却是符其实.

 

 

 

 

1
0
分享到:
评论
3 楼 name327 2014-11-03  
LZ文章看似杂乱,但是点点说到NIO要点,需要经过大量的实验才能得出的结果,赞一个。
2 楼 沙舟狼客 2013-07-11  
你好楼主,有空帮忙分析一下mina2.0.7的异常:
java.nio.channels.CancelledKeyException
	at sun.nio.ch.SelectionKeyImpl.ensureValid(SelectionKeyImpl.java:73)
	at sun.nio.ch.SelectionKeyImpl.interestOps(SelectionKeyImpl.java:77)
	at org.apache.mina.transport.socket.nio.NioProcessor.setInterestedInWrite(NioProcessor.java:256)
	at org.apache.mina.transport.socket.nio.NioProcessor.setInterestedInWrite(NioProcessor.java:44)
	at org.apache.mina.core.polling.AbstractPollingIoProcessor.flushNow(AbstractPollingIoProcessor.java:891)
	at org.apache.mina.core.polling.AbstractPollingIoProcessor.flush(AbstractPollingIoProcessor.java:789)
	at org.apache.mina.core.polling.AbstractPollingIoProcessor.access$700(AbstractPollingIoProcessor.java:67)
	at org.apache.mina.core.polling.AbstractPollingIoProcessor$Processor.run(AbstractPollingIoProcessor.java:1129)
	at org.apache.mina.util.NamePreservingRunnable.run(NamePreservingRunnable.java:64)
	at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
	at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
	at java.lang.Thread.run(Thread.java:724)
1 楼 t8500071 2010-08-16  
引用
if remove the current selectedKey from selector.selectedKeys()[Set] but don't sk.interestOps(sk.interestOps()& (~sk.readyOps()));将导致 selector.select(...) not block [select() not block several times, or excepted exception]


就是因为这个问题,困扰了我很久。

相关推荐

    java多线程程序设计:Java NIO+多线程实现聊天室

    java多线程程序设计:Java NIO+多线程实现聊天室 Java基于多线程和NIO实现聊天室 涉及到的技术点 线程池ThreadPoolExecutor 阻塞队列BlockingQueue,生产者消费者模式 Selector Channel ByteBuffer ProtoStuff 高...

    多线程精品资源--Java NIO+多线程实现聊天室.zip

    1. 如何创建和管理线程,以及如何在多线程环境中进行有效的通信和同步。 2. Java NIO的基本组件,如通道(Channel)、缓冲区(Buffer)、选择器(Selector)以及如何使用它们来实现非阻塞I/O。 3. 聊天室应用的设计...

    Java Socket学习---nio实现阻塞多线程通信

    总的来说,Java NIO在实现阻塞多线程通信时,通过`Selector`监控多个`Channel`,减少了线程的创建和管理,提高了系统资源的利用率。同时,`ByteBuffer`的使用降低了内存拷贝的开销,提升了性能。通过`EchoServer`和`...

    java NIO和java并发编程的书籍

    java NIO和java并发编程的书籍java NIO和java并发编程的书籍java NIO和java并发编程的书籍java NIO和java并发编程的书籍java NIO和java并发编程的书籍java NIO和java并发编程的书籍java NIO和java并发编程的书籍java...

    JavaNIO chm帮助文档

    Java NIO系列教程(一) Java NIO 概述 Java NIO系列教程(二) Channel Java NIO系列教程(三) Buffer Java NIO系列教程(四) Scatter/Gather Java NIO系列教程(五) 通道之间的数据传输 Java NIO系列教程(六)...

    java多线程nio服务器

    Java NIO服务器的多线程设计有助于提高服务器的并发性能,特别是在高并发场景下,可以有效地利用系统资源,避免大量线程导致的内存消耗和上下文切换开销。同时,通过选择器的使用,减少了对主线程的占用,使得服务器...

    java NIO socket聊天室

    使用NIO socket不需要多线程来处理多个连接的请求,效率非常高 可以作为NIO socket入门的例子,Reactor模式,重点理解key.attach, jar文件里包含了源代码 1,运行server.bat启动服务器,可以打开编辑,修改端口号 ...

    基于事件的_NIO_多线程服务器

    在Java的网络编程中,NIO(Non-blocking I/O)作为一种高效的数据处理模式,自JDK 1.4版本引入以来,逐渐成为了开发高性能网络应用的重要工具之一。与传统的阻塞I/O相比,NIO通过非阻塞的方式减少了线程的开销,特别...

    java NIO.zip

    自Java 1.4版本引入NIO后,它为Java开发者提供了更高效的数据传输方式,尤其是在处理大量并发连接时。NIO的核心在于通道(Channels)和缓冲区(Buffers)的概念,与传统的流(Streams)有所不同。 1. **通道...

    使用多线程的NIO构建简易的多线程java服务器

    在Java编程中,使用非阻塞I/O(Non-blocking Input/Output,NIO)和多线程技术可以构建高效、可扩展的服务器。本篇我们将深入探讨如何利用NIO和多线程来创建一个简单的Java服务器。首先,我们需要理解NIO的基本概念...

    Java NIO英文高清原版

    6. **多路复用器(Multiplexing)**:Java NIO的选择器实现了I/O多路复用,即单个线程可以同时处理多个连接,这在处理大量并发连接时非常有用。 7. **管道(Pipe)**:管道是两个线程间进行单向数据传输的通道。一...

    java多线程读取文件

    Java多线程读大文件 java多线程写文件:多线程往队列中写入数据

    java NIO技巧及原理

    4. **线程安全**:在多线程环境下使用NIO时,需要确保对共享资源的正确同步。 总之,Java NIO提供了强大的I/O能力,但同时也需要开发者对非阻塞I/O和多路复用有深入理解,才能充分发挥其优势,避免潜在的陷阱。学习...

    java NIO 视频教程

    Java NIO(New IO)是一个可以替代标准Java IO API的IO API(从Java 1.4开始),Java NIO提供了与标准IO不同的IO工作方式。 Java NIO: Channels and Buffers(通道和缓冲区) 标准的IO基于字节流和字符流进行操作的,...

    java nio 包读取超大数据文件

    NIO在Java 1.4版本引入,并在后续版本中得到了进一步增强和完善。相较于传统的Java IO,NIO具有更高的性能和更丰富的功能,尤其适合处理大文件或高并发场景。 #### 二、Java NIO关键组件 Java NIO的核心组件包括: ...

    Java NIO 中文 Java NIO 中文 Java NIO 中文文档

    Java NIO 深入探讨了 1.4 版的 I/O 新特性,并告诉您如何使用这些特性来极大地提升您所写的 Java 代码的执行效率。这本小册子就程序员所面临的有代表性的 I/O 问题作了详尽阐述,并讲解了 如何才能充分利用新的 I/O ...

    JAVA NIO 按行读取大文件支持 GB级别-修正版

    由于对于本程序 116个字节以上的行才有意义,所以 在next实现方法中,有对 116 长度的判断,否则返回 null 修正了之前版本中的问题: 修正后的方法 private int readByte() throws IOException{ fbb.rewind(); ...

    一个java NIO的例子

    而Java NIO引入了选择器(Selector)和通道(Channel)的概念,允许单个线程同时处理多个连接,大大提高了系统在高并发环境下的性能。 本例子中的"NioServer"可能是一个简单的Java NIO服务器端程序,用于演示如何...

    java NIO实例

    传统的Java I/O模型(BIO)在处理大量并发连接时效率较低,因为它基于阻塞模式,一个线程只能处理一个连接,而NIO则允许单个线程同时处理多个连接,大大提高了性能。 `NIOServer.java`和`NIOClient.java`这两个文件...

Global site tag (gtag.js) - Google Analytics