各位大大请教一个问题:Netty 在主从 Reactor 多线程下服务端启动时候会创建创建主从线程池 boss 和 work,但是服务端启动创建的一个 NioServerSocketChannel 实例只会 register boos 线程池中的一个 NioEvnetLoop 线程,也就说虽然创建了 boss 线程池但是实际上只是用了其中的一个线程,除非绑定多个端口。
有几点疑问:(1)在绑定一个端口的情况下,创建一个 boss 线程池是没有必要的吧?(2)网上说 Reactor 主从多线程模型优势在于:服务端用于接收客户端连接的不再是个 1 个单独的 NIO 线程,这种说法是有问题的吧(在只绑定一个端口的情况下)?
![]() | 1 BBCCBB 2018-01-26 16:55:25 +08:00 我只见过一个 boss 用于 select, 一个或多个 worker 负责读写... |
![]() | 3 anthow 2018-01-26 17:10:21 +08:00 如果绑定一个端口的话,线程池的确没啥必要... |
4 jy02405651 2018-01-26 17:17:08 +08:00 Netty 的服务器端的 acceptor 阶段, 没有使用到多线程 |
![]() | 5 tuzhenyu OP @jy02405651 那 boss 线程池的作用是啥呢,仅仅是用作绑定多个端口的情况吗? |
![]() | 6 tuzhenyu OP @anthow 书上说 Reactor 主从多线程模型优势在于:服务端用于接收客户端连接的不再是个 1 个单独的 NIO 线程,这句话是指的绑定多个端口的情况吗? |
![]() | 7 BBCCBB 2018-01-26 17:23:36 +08:00 @tuzhenyu 我不知道多个线程处理 select 可不可行, 不过多个 boss 负责 select 感觉没有必要,也没这方面的经验, 如果你有看到相关的资料,请给我看一下,让我涨涨知识 |
![]() | 8 BBCCBB 2018-01-26 17:26:58 +08:00 这是我原来看相关 io 模型的文章和 Doug lea 大神的论文 [Scalable IO in Java]( http://www.cnblogs.com/luxiaoxun/archive/2015/03/11/4331110.html) [Doug lea Scalable IO in Java]( http://gee.cs.oswego.edu/dl/cpjslides/nio.pdf) |
9 fovecifer 2018-01-26 17:27:37 +08:00 谈谈我的理解 1. boss 线程一般只负责 accept 新链接,这个工作一般情况下单个线程肯定够了 2. 只有一个线程的线程池也是线程池!这是抽象概念问题,请参考 JDK 并发包里的线程池 3. 据我所知处理网络 IO 的最优解就是一个线程负责 accept,其他 N 个线程负责具体的 IO 操作 |
![]() | 10 tuzhenyu OP @BBCCBB 我是在<Netty 权威指南>上看的,应该是作者的措辞不够严谨,一个端口只能一个 boss 线程负责 acceept,谢谢~ |
![]() | 12 seaswalker 2018-01-26 18:06:18 +08:00 从源码的角度应该是这样的: boss 线程在 Netty 里就是 NioEventLoopGroup,其父类的 NioEventLoop 的 processSelectedKey 方法负责处理 epoll 事件,之后由 AbstractNioMessageChannel 的 read 方法触发 BossGroup 上的 事件处理器,BossGroup 上其实只有一个,就是 ServerBootstrapAcceptor 这货,然后由这货将子 channel 注册到 ChildGroup 上去,这中间全部是一个线程完成,应该可以证实你的说法。 |
![]() | 13 mazai 2019-12-02 19:06:25 +08:00 实际上 boosGroup 和 workerGroup 用的都是同一个线程池,并没有单独给 boos 一个线程池。 |