以前,当我使用 disruptor 的单一生产者模式时,例如
new Disruptor<ValueEvent>(ValueEvent.EVENT_FACTORY,
2048, moranContext.getThreadPoolExecutor(), ProducerType.Single,
new BlockingWaitStrategy())
性能不错。现在我处于多个线程将写入单个环形缓冲区的情况。我发现 ProducerType.Multi
使代码比单一生产者模式慢几倍。我不会接受这种糟糕的表现。那么我应该使用单生产者模式,而多个线程使用锁调用相同的事件发布方法,可以吗?谢谢。
最佳答案
我对 Disruptor 有点陌生,但经过广泛的测试和试验后,我可以说 ProducerType.MULTI 对于 2 个或更多生产者线程更准确、更快。
在 MacBook 上有 14 个生产者线程时,ProducerType.SINGLE 显示发布的事件多于消耗的事件,即使我的测试代码正在等待所有生产者结束(他们在运行 10 秒后这样做),然后等待破坏者结尾。不太准确:那些额外发布的事件去了哪里?
Driver start: PID=38619 Processors=8 RingBufferSize=1024 Connections=Reuse Publishers=14[SINGLE] Handlers=1[BLOCK] HandlerType=EventHandler<Event>
Done: elpased=10s eventsPublished=6956894 eventsProcessed=4954645
Stats: events/sec=494883.36 sec/event=0.0000 CPU=82.4%
使用 ProducerType.MULTI,发布的事件比 SINGLE 少,但在同样的 10 秒内实际消耗的事件比 SINGLE 多。对于 MULTI,所有 已发布的事件都会被消耗掉,这正是我所期望的,因为驱动程序会在耗时到期后以谨慎的方式自行关闭:
Driver start: PID=38625 Processors=8 RingBufferSize=1024 Connections=Reuse Publishers=14[MULTI] Handlers=1[BLOCK] HandlerType=EventHandler<Event>
Done: elpased=10s eventsPublished=6397109 eventsProcessed=6397109
Stats: events/sec=638906.33 sec/event=0.0000 CPU=30.1%
同样:2 个或更多生产者:使用 ProducerType.MULTI。
顺便说一句,每个 Producer 通过获取下一个槽,更新事件,然后发布槽,直接发布到环形缓冲区。每当调用 onEvent 方法时,处理程序都会获取事件。没有额外的队列。非常简单。
关于java - 与单生产者模式相比,lmax disruptor 在多生产者模式下太慢,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18997398/