簡體   English   中英

Java 性能逐漸下降

[英]Java performance gradually degrades

我有一個 Java 類,它執行以下操作:

public void slowsDownOverTime() {
    for (int i=0 ; i<nIter ; i++) {
        BigObject bigObject = new BigObject();
        // some code here that populates big object ...
        CustomSerializer.write(bigObject);
    }
}

我觀察到的是,隨着代碼迭代,序列化程序編寫所需的時間越來越長。 啟動時,序列化程序以毫秒為單位運行; 經過幾萬次迭代,運行需要幾秒鍾。

序列化程序寫入的磁盤遠未滿,並且在發生這種情況時,正在使用的 Java 堆空間遠未達到最大值。

我盡可能減少了在此周期中創建和銷毀的對象的數量和大小。 這基本上耗盡了我解決此類問題的工具包!

任何關於我如何理解和糾正逐漸性能下降的建議將不勝感激!

我認為,這是由遺漏的代碼引起的(這里的一些代碼填充了大對象......)。 嘗試這個:

public void slowsDownOverTime() {
    BigObject bigObject = new BigObject();
    // some code here that populates big object ...
    for (int i=0 ; i<nIter ; i++) {
        CustomSerializer.write(bigObject);
    }
}

這將始終寫入相同的對象,我希望這不會降低性能。

我認為被遺漏的代碼構建了一個正在被bigObject引用的不斷增長的數據結構。 請記住,在序列化時,Java 會深入遍歷所有依賴對象並序列化所有依賴對象。 所以每次迭代都會寫入越來越多的數據。 這可能是降低性能和使用大量磁盤空間的原因。

在對 jvisualvm 的分析器進行了多次無果而終的嘗試之后,我求助於添加大量日志記錄。 這給了我一個線索,即問題出在為填充 BigObject 而執行的 Hibernate 操作中。 我能夠通過在我檢索到的每個對象后立即驅逐它來解決性能問題。

我不是 Hibernate 專家,但我認為發生的事情是,即使對象超出了我代碼中的范圍(因此被垃圾收集),Hibernate 仍在其緩存中保留每個對象的副本. 然后當它執行下一次檢索時,它將檢索到的對象與所有緩存的對象進行比較。 隨着緩存數量的增加,此操作將花費越來越長的時間。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM