/** * AIO服务端 * * @author xiangwang */public class AioServer {public void start() throws InterruptedException, IOException {AsynchronousServerSocketChannel channel = AsynchronousServerSocketChannel.open();if (channel.isOpen()) {// socket接受缓冲区recbuf大小channel.setOption(StandardSocketOptions.SO_RCVBUF, 4 * 1024);// 端口重用,防止进程意外终止,未释放端口,重启时失败// 因为直接杀进程,没有显式关闭套接字来释放端口,会等待一段时间后才可以重新use这个关口// 解决办法就是用SO_REUSEADDRchannel.setOption(StandardSocketOptions.SO_REUSEADDR, true);channel.bind(new InetSocketAddress(8080));} else {throw new RuntimeException("channel not opened!");}// 处理client连接channel.accept(null, new AioServerHandler(channel));System.out.println("server started");// 阻塞主进程for(;;) {TimeUnit.SECONDS.sleep(1);}}public static void main(String[] args) throws IOException, InterruptedException {AioServer server = new AioServer();server.start();}}/** * AIO服务端CompletionHandler * * @author xiangwang */public class AioServerHandler implements CompletionHandler<AsynchronousSocketChannel, Void> {private final AsynchronousServerSocketChannel serverChannel;private final CharsetDecoder decoder = Charset.defaultCharset().newDecoder();private final BufferedReader input = new BufferedReader(new InputStreamReader(System.in));public AioServerHandler(AsynchronousServerSocketChannel serverChannel) {this.serverChannel = serverChannel;}@Overridepublic void failed(Throwable exc, Void attachment) {// 处理下一次的client连接serverChannel.accept(null, this);}@Overridepublic void completed(AsynchronousSocketChannel result, Void attachment) {// 处理下一次的client连接,类似链式调用serverChannel.accept(null, this);try {// 将输入内容写到bufferString line = input.readLine();result.write(ByteBuffer.wrap(line.getBytes()));// 在操作系统中的Java本地方法native已经把数据写到了buffer中// 这里只需要一个缓冲区能接收就行了ByteBuffer buffer = ByteBuffer.allocate(1024);while (result.read(buffer).get() != -1) {buffer.flip();System.out.println("from client: " + decoder.decode(buffer).toString());if (buffer.hasRemaining()) {buffer.compact();} else {buffer.clear();}// 将输入内容写到bufferline = input.readLine();result.write(ByteBuffer.wrap(line.getBytes()));}} catch (InterruptedException | ExecutionException | IOException e) {e.printStackTrace();}}}执行测试后显示,不管是在客户端还是在服务端,读写完全是异步的 。
感谢您的大驾光临!咨询技术、产品、运营和管理相关问题,请关注后留言 。欢迎骚扰,不胜荣幸~
经验总结扩展阅读
- 煮干饭的比例水和饭的比例是多少
- 立秋分上午和下午吗
- 蟑螂的生活环境和特征
- 带泥胡萝卜和不带泥胡萝卜一样的吗
- 特奥会和残奥会的区别
- redmi k40和k40pro区别_手机参数对比
- 天玑920和天玑1000+性能对比_哪款性能更好
- 小米12和荣耀magic3哪个好-小米12和荣耀magic3参数对比
- 白羊座和狮子座谁更适合当女朋友
- 白羊座和巨蟹座谁更适合当女朋友