生活随笔
收集整理的這篇文章主要介紹了
问道Netty。持续更新。。。
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
概念
Zero Copy
- 0拷貝,速度快
- 操作數據時, 不需要將數據 buffer 從一個內存區域拷貝到另一個內存區域. 因為少了一次內存的拷貝, 因此 CPU 的效率就得到的提升.
- 在 OS 層面上的 Zero-copy 通常指避免在 用戶態(User-space) 與 內核態(Kernel-space) 之間來回拷貝數據. 例如 Linux 提供的 mmap 系統調用, 它可以將一段用戶空間內存映射到內核空間, 當映射成功后, 用戶對這段內存區域的修改可以直接反映到內核空間; 同樣地, 內核空間對這段區域的修改也直接反映用戶空間. 正因為有這樣的映射關系, 我們就不需要在 用戶態(User-space) 與 內核態(Kernel-space) 之間拷貝數據, 提高了數據傳輸的效率.
而需要注意的是, Netty 中的 Zero-copy 與上面我們所提到到 OS 層面上的 Zero-copy 不太一樣, Netty的 Zero-coyp 完全是在用戶態(Java 層面)的, 它的 Zero-copy 的更多的是偏向于 優化數據操作 這樣的概念.
實操
代碼
服務器
新建Maven項目:
添加插件:
<plugin><groupId>org.codehaus.mojo
</groupId><artifactId>exec-maven-plugin
</artifactId><version>1.6.0
</version><executions><execution>
<phase>test
</phase>
<goals>
<goal>java
</goal></goals></execution></executions><configuration>
<mainClass>com.cc.netty.server.EchoServer
</mainClass>
<arguments><argument>argument1
</argument>
</arguments>
<systemProperties><systemProperty><key>myproperty
</key><value>myvalue
</value></systemProperty>
</systemProperties></configuration></plugin>
執行mvn exec:java:
報錯:
說明插件里的參數有問題。
package com.cc.netty.test;import io.netty.bootstrap.ServerBootstrap;
import io.netty.buffer.ByteBuf;
import io.netty.buffer.Unpooled;
import io.netty.channel.*;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.SocketChannel;
import io.netty.channel.socket.nio.NioServerSocketChannel;
import io.netty.handler.codec.string.StringDecoder;
import io.netty.handler.codec.string.StringEncoder;
import io.netty.handler.timeout.ReadTimeoutHandler;
import io.netty.util.CharsetUtil;
import io.netty.util.ReferenceCountUtil;import java.util.Scanner;
public class NettyServer {public static void main(String[] args
) throws Exception {new NettyServer().run(8666);}public void run(int port
) throws Exception {EventLoopGroup bossGroup
= new NioEventLoopGroup();EventLoopGroup workGroup
= new NioEventLoopGroup();System.out
.println("準備運行端口:" + port
);try {ServerBootstrap serverBootstrap
= new ServerBootstrap();serverBootstrap
= serverBootstrap
.group(bossGroup
, workGroup
).channel(NioServerSocketChannel.class).option(ChannelOption.SO_BACKLOG
, 128).childOption(ChannelOption.SO_KEEPALIVE
, true).childHandler(new ChildChannelHandler());ChannelFuture future
= serverBootstrap
.bind(port
).sync();future
.channel().closeFuture().sync();} finally {workGroup
.shutdownGracefully();bossGroup
.shutdownGracefully();}}
}
class ChildChannelHandler extends ChannelInitializer<SocketChannel> {protected void initChannel(SocketChannel socketChannel
) throws Exception {
socketChannel
.pipeline().addLast(new StringDecoder());socketChannel
.pipeline().addLast(new StringEncoder());socketChannel
.pipeline().addLast(new ReadTimeoutHandler(60));socketChannel
.pipeline().addLast(new DiscardServerHandler());}
}
class DiscardServerHandler extends ChannelHandlerAdapter {@Overridepublic void channelRead(ChannelHandlerContext ctx
, Object msg
) {try {System.out
.println(String.format("%s === %s","收到信息",msg
));
System.out
.println("傳輸內容是");
ByteBuf resp
= Unpooled.copiedBuffer("服務端收到信息,ack$".getBytes());ctx
.writeAndFlush(resp
);
} finally {System.out
.println(msg
);ReferenceCountUtil.release(msg
);}}@Overridepublic void exceptionCaught(ChannelHandlerContext ctx
, Throwable cause
) throws Exception {cause
.printStackTrace();ctx
.close();}}
package com.cc.netty.test;import io.netty.bootstrap.Bootstrap;
import io.netty.buffer.ByteBuf;
import io.netty.buffer.Unpooled;
import io.netty.channel.*;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.SocketChannel;
import io.netty.channel.socket.nio.NioSocketChannel;
import io.netty.handler.codec.DelimiterBasedFrameDecoder;
import io.netty.util.CharsetUtil;
import io.netty.util.ReferenceCountUtil;
public class TimeClient {public static void main(String[] args
) throws Exception {new TimeClient().connect(8666, "localhost");}public void connect(int port
, String host
) throws Exception {System.out
.println("連接=>" + host
+ ":" + port
);EventLoopGroup eventLoopGroup
= new NioEventLoopGroup();try {Bootstrap bootstrap
= new Bootstrap();bootstrap
.group(eventLoopGroup
).channel(NioSocketChannel.class).option(ChannelOption.TCP_NODELAY
, true).handler(new ChannelInitializer<SocketChannel>() {protected void initChannel(SocketChannel socketChannel
) throws Exception {ByteBuf byteBuf
= Unpooled.copiedBuffer("$".getBytes());socketChannel
.pipeline().addLast(new DelimiterBasedFrameDecoder(1024, byteBuf
));socketChannel
.pipeline().addLast(new TimeClientHandler());}});ChannelFuture future
= bootstrap
.connect(host
, port
).sync();future
.channel().closeFuture().sync();} finally {eventLoopGroup
.shutdownGracefully();}}
}class TimeClientHandler extends ChannelHandlerAdapter {private byte[] req
;public TimeClientHandler() {req
= "中國必勝!武漢加油!".getBytes();
}@Overridepublic void channelActive(ChannelHandlerContext ctx
) throws Exception {ByteBuf message
= null;for (int i
= 0; i
< 5; i
++) {message
= Unpooled.buffer(req
.length
);message
.writeBytes(req
);ctx
.writeAndFlush(message
);}}@Overridepublic void channelRead(ChannelHandlerContext ctx
, Object msg
) {try {ByteBuf in
= (ByteBuf) msg
;System.out
.println(in
.toString(CharsetUtil.UTF_8
));} finally {ReferenceCountUtil.release(msg
);}}@Overridepublic void exceptionCaught(ChannelHandlerContext ctx
, Throwable cause
) throws Exception {cause
.printStackTrace();ctx
.close();}}
總結
以上是生活随笔為你收集整理的问道Netty。持续更新。。。的全部內容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。