gpt4 book ai didi

java - 如何分析 Java 中的线程转储以最大限度地减少高 CPU 使用率

转载 作者:行者123 更新时间:2023-12-02 05:46:24 25 4
gpt4 key购买 nike

我正在尝试使用 Disruptor 读取文本文件并插入数据库。

但是我发现CPU使用率太高(200%,根据top命令)。

我是性能调优和线程转储分析的新手。我不知道出了什么问题。

因此,我执行 top -H 并找到两个最高的线程(均为 99%),并找到线程转储:

"main" prio=10 tid=0x00007f54a4006800 nid=0x79ab runnable [0x00007f54a8340000]
java.lang.Thread.State: RUNNABLE
at java.lang.Thread.yield(Native Method)
at com.lmax.disruptor.SingleProducerSequencer.next(SingleProducerSequencer.java:104)
at com.lmax.disruptor.SingleProducerSequencer.next(SingleProducerSequencer.java:79)
at com.lmax.disruptor.RingBuffer.next(RingBuffer.java:207)
at com.xxx.xxx.connectivity.quickfixj.FixMessageReceiver.onMessage(FixMessageReceiver.java:105)
at com.xxx.xxx.database.DatabaseService.start(DatabaseService.java:110)
at com.xxx.xxx.database.DatabaseService.main(DatabaseService.java:168)


"pool-2-thread-1" prio=10 tid=0x00007f54a426d800 nid=0x79bc runnable [0x00007f5492a37000]
java.lang.Thread.State: RUNNABLE
at java.lang.Thread.yield(Native Method)
at com.lmax.disruptor.SingleProducerSequencer.next(SingleProducerSequencer.java:104)
at com.lmax.disruptor.SingleProducerSequencer.next(SingleProducerSequencer.java:79)
at com.lmax.disruptor.RingBuffer.next(RingBuffer.java:207)
at com.cimb.reporting.connectivity.jms.DatabaseEventHandler.publish2DbRingBuffer(DatabaseEventHandler.java:49)
at com.xxx.xxx.connectivity.jms.DatabaseEventHandler.onEvent(DatabaseEventHandler.java:39)
at com.xxx.xxx.connectivity.jms.DatabaseEventHandler.onEvent(DatabaseEventHandler.java:15)
at com.lmax.disruptor.BatchEventProcessor.run(BatchEventProcessor.java:133)
at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:895)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:918)
at java.lang.Thread.run(Thread.java:662)

基本上这两个线程将向 Disruptor 发布数据。我以这种方式创建 Disruptor:

Disruptor<TradeEvent> disruptor = new Disruptor<TradeEvent>(TradeEvent.TRADE_EVENT_FACTORY,
properties.dbRingbufferSize(), Executors.newCachedThreadPool(),
ProducerType.SINGLE, new BlockingWaitStrategy());

请帮助我分析线程转储以找到 CPU 使用率高的根本原因。

最佳答案

面临完全相同的问题:我的机器 Intel Core i3-3220、16GB 内存、一个代理 (Xmx 2G)、一个客户端 (Xmx2G) 上 100% cpu 使用率,并且环形缓冲区中没有任何消息。

快速分析显示 Thread.yield() 消耗了大约 70-80% 的 cpu。

事实证明,对于我来说,YieldingWaitStrategy 并不是一个合适的策略。因此,在我的例子中,快速解决方法是将等待策略设置为 BlockingWaitStrategy:

Disruptor<MessageEvent> disruptor = new Disruptor<MessageEvent>(eventFactory, RING_BUFFER_SIZE, executor, ProducerType.SINGLE, new BlockingWaitStrategy());

更新

YieldingWaitStrategy 的 JProfiler enter image description here

关于java - 如何分析 Java 中的线程转储以最大限度地减少高 CPU 使用率,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24028755/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com