epoll,java
<link rel="stylesheet" href="https://js.how234.com/third-party/SyntaxHighlighter/shCoreDefault.css" type="text/css" /><script type="text/javascript" src="https://js.how234.com/third-party/SyntaxHighlighter/shCore.js"></script><script type="text/javascript"> SyntaxHighlighter.all(); </script>
java epoll是什麼,讓我們一起了解一下?
epoll是Linux核心為處理大批量檔案描述符而作了改進的poll,是Linux下多路複用IO介面select或poll的增強版本,能顯著提高程式在大量併發連線中只有少量活躍的情況下的系統CPU利用率。
如何實現epoll的介面?
1、建立epoll控制代碼。
2、將被監聽的描述符新增到epoll控制代碼或從epool控制代碼中刪除或者對監聽事件進行修改。
3、等待事件觸發,當超過timeout還沒有事件觸發時,就超時。
在Java中epoll的優點有哪些?
1、支援一個程序開啟大數目的socket描述符。
2、IO效率不隨FD數目增加而線性下降。
3、沒有使用mmap加速核心與使用者空間的訊息傳遞。
如何使用多路複用的服務端程式,來演示JavaAPI中提供的方法與底層epoll函式實現的具體關係?
首先程式執行後服務端啟動並繫結9090埠,等待客戶端連線,讀取到客戶端訊息後再直接把訊息後回覆給客戶端。
示例程式碼如下:
import java.io.IOException;import java.net.InetSocketAddress;import java.nio.ByteBuffer;import java.nio.channels.*;import java.util.Iterator;import java.util.Set;public class SocketMultiplexIO { private static Selector selector; public static void main(String[] args) throws Exception { ServerSocketChannel serverSocketChannel = ServerSocketChannel.open(); serverSocketChannel.bind(new InetSocketAddress(9090)); serverSocketChannel.configureBlocking(false); selector = Selector.open(); serverSocketChannel.register(selector, SelectionKey.OP_ACCEPT); System.out.println("服務端啟動了。。。"); while (true) { Set<SelectionKey> keys = selector.keys(); System.out.println("當前epoll註冊的事件:" + keys.size()); while (selector.select() > 0) { Set<SelectionKey> selectionKeys = selector.selectedKeys(); Iterator<SelectionKey> iterator = selectionKeys.iterator(); while (iterator.hasNext()) { SelectionKey selectionKey = iterator.next(); iterator.remove(); if (selectionKey.isAcceptable()) { System.out.println("有一個客戶端連線了。。。"); acceptHandler(selectionKey); } else if (selectionKey.isReadable()) { selectionKey.cancel(); System.out.println("cancel函式,取消了accept事件"); readHandler(selectionKey); } } } } } private static void readHandler(SelectionKey key) { SocketChannel client = (SocketChannel) key.channel(); ByteBuffer buffer = (ByteBuffer) key.attachment(); buffer.clear(); int read; try { while (true) { read = client.read(buffer); if (read > 0) { buffer.flip(); while (buffer.hasRemaining()) { client.write(buffer); } buffer.clear(); } else if (read == 0) { break; } else { client.close(); break; } } } catch (IOException e) { e.printStackTrace(); } } private static void acceptHandler(SelectionKey selectionKey) throws IOException { ServerSocketChannel serverSocketChannel = (ServerSocketChannel) selectionKey.channel(); SocketChannel accept = serverSocketChannel.accept(); accept.configureBlocking(false); ByteBuffer byteBuffer = ByteBuffer.allocateDirect(1024); accept.register(selector, SelectionKey.OP_READ, byteBuffer); }}