0

我正在 TCP/IP 之上实现一个二进制协议,并使用 Netty 来实现这一点。我的问题是性能相当差(600 msg/s)。我作为客户端连接到仅具有一个连接的服务器。当我使用 JTop 调查运行实例时,我看到 Netty 非常频繁地使用 1 个工作线程,而其他 5 个工作线程什么也没做(0% 使用率)。我在网上挖掘,我发现的只是提到了 ExecutionHandler。但是,如果这 6 个工作线程就足够了,我为什么要使用它。还是我误解了 Netty 如何使用这些线程?

我的 Netty 初始化代码:

this.channelFactory = new NioClientSocketChannelFactory(this.executors, DaemonExecutors.newCachedDaemonThreadPool(), 1, 6);
this.clientBootstrap = new ClientBootstrap(channelFactory);
this.channelGroupHandler = new ClientChannelGroupHandler(this.channels);
this.clientBootstrap.getPipeline().addLast("ChannelGroupHandler", this.channelGroupHandler);

感谢马图斯的任何提示

4

2 回答 2

2

NIO,或者更确切地说,NIO 的非阻塞版本(“新”I/O)允许您将单个线程用于多个连接,因为线程不会阻塞(因此得名)读/写操作。阻塞 I/O 需要每个连接都有一个线程,因为阻塞会阻止您处理不同连接之间的流量。

这使您可以执行更有效的通信,因为您不再有线程开销。

这里有一个不错的教程(最初的 Oracle 教程似乎已经从 Google 的脸上消失了)。

于 2013-11-11T13:10:11.937 回答
0

您只看到一个工作线程正在使用的原因是因为您只与服务器建立了一个连接。如果你建立了多个连接,就会使用更多的工作线程。

如果每个连接的工作都适合并行化,那么您可以实现一个在内部使用线程的处理程序,但 Netty 不会为您这样做。

至于 NIO/OIO 的区别,确实 NIO 的想法是让一个线程处理多个连接的事件。然而,这并不意味着一个线程将处理所有的工作。“单线程”仅将工作分派给其他(即工作线程)线程。

这是 Netty 文档的摘录:

线程如何工作 NioServerSocketChannelFactory 中有两种类型的线程;一个是老板线程,另一个是工作线程。

Boss 线程 每个绑定的 ServerSocketChannel 都有自己的 Boss 线程。比如你打开了80、443等两个服务器端口,就会有两个boss线程。老板线程接受传入的连接,直到端口未绑定。成功接受连接后,boss 线程将接受的 Channel 传递给 NioServerSocketChannelFactory 管理的工作线程之一。

工作线程 一个 NioServerSocketChannelFactory 可以有一个或多个工作线程。工作线程以非阻塞模式对一个或多个 Channel 执行非阻塞读写。

于 2013-11-11T14:04:07.040 回答