js内存泄露 垃圾回收_Java内存体系结构(模型),垃圾回收和内存泄漏
js內存泄露 垃圾回收
Java內存架構(Java內存模型)
上面是堆的Java內存模型以及Java虛擬機(JVM)中運行的任何Java應用程序的PermGen。 還提供了比率,以使您更好地了解如何在每種生成類型之間分配允許的內存。 以上所有內容完全適用于Java 1.7版(含)。 上面也稱為內存模型的“管理區域”。
除上述內容外,還有一個堆棧區域,可以使用-Xss選項進行配置。 該區域保存堆上的引用,本機引用,pc寄存器,代碼緩存和所有線程的局部變量。 這也稱為內存模型的“本地區域”。
Java內存模型的受管區域(Java內存體系結構)
[年輕一代/苗圃]伊甸園空間
首先在伊甸園空間中創建所有新對象。 一旦達到由JVM確定的任意閾值,就會啟動次要垃圾回收(Minor GC)。它首先刪除所有非引用對象,并將引用對象從“ eden”和“ from”移到“ to”幸存者空間。 GC結束后,將交換“從”和“到”角色(名稱)。
[年輕一代/苗圃]幸存者1(來自)
這是幸存者空間的一部分(您可能會認為這是幸存者空間中的角色 )。 這是上一個垃圾回收(GC)期間的“收件人”角色。
[年輕一代/苗圃] Suvrivor 2(至)
這也是幸存者空間的一部分(您可能認為這也是幸存者空間中的角色 )。 在這里,在GC期間,所有引用的對象
從'from'和'eden'移到。
[上一代]終身任職
根據閾值限制,可以使用-XX:+ PrintTenuringDistribution進行檢查,該限制按年齡顯示對象(以字節為單位的空間)–將對象從“到” 幸存者空間移動到Tenured空間。 “年齡”是指它在幸存者空間內移動的次數。 還有其他重要標志,例如-XX:InitialTenuringThreshold,-XX:MaxTenuringThreshold和-XX:TargetSurvivorRatio ,這些標志可導致對保有權空間和幸存者空間進行最佳利用。 通過設置-XX:InitialTenuringThreshold和-XX:MaxTenuringThreshold,我們允許'Age'的初始值和最大值,同時保持-XX:+ NeverTenure和-XX指定的'Survivor(To)'中的利用率百分比。正如他們建議的那樣,+ AlwaysTenure用于永遠不保管對象(使用風險較大 ),而相反的用法是始終保管,即始終使用“老一代”。 這里發生的垃圾收集是主要垃圾收集(主要GC)。 通常在堆已滿或舊代已滿時觸發。 這通常是接管執行垃圾回收的' Stop-the-World '事件或線程。 還有另一種稱為完全垃圾收集(Full GC)的GC,它涉及其他內存區域,例如permgen空間。
與整個堆相關的其他重要且有趣的標志是-XX:SurvivorRatio和-XX:NewRatio ,它們指定eden空間與幸存者空間的比率以及舊一代與新一代的比率。
[永久世代] Permgen空間
“ Permgen”用于存儲以下信息:常量池(內存池),字段和方法數據以及代碼。 他們每個人的名字都暗示著相同的細節。
垃圾收集算法
串行GC(-XX:UseSerialGC):年輕一代和老一代的GC
為年輕和終身一代使用簡單的標記掃描緊湊循環。 這對于客戶端系統以及內存占用量少和cpu較小的系統來說是一個好選擇
并行GC(-XX:UseParallelGC):年輕一代和老一代的GC
這使用了N個線程,可以使用-XX:ParallelGCThreads = N進行配置,這里N也是CPU內核的數量。 用于垃圾收集。 它在Young代中將這N個線程用于GC,而在Old代中僅使用一個線程。
并行舊GC(-XX:UseParallelOldGC):年輕一代和老一代的GC
這與并行GC相同,除了在舊一代和年輕一代中都使用N個線程進行GC。
并發標記和掃描GC(-XX:ConcMarkSweepGC):舊Generaton上的GC
顧名思義,CMS GC最大限度地減少了GC所需的停頓時間。 創建高響應性的應用程序最有用,并且僅在舊版本中才進行GC。 它為GC創建了多個線程,這些線程與應用程序線程并發工作,可以使用-XX:ParallelCMSThreads = n指定這些線程。
G1 GC(-XX:UseG1GC):年輕一代和老年人一代的GC(通過將堆分成相等大小的區域)
這是一個并行,并發且遞增壓縮的低暫停垃圾收集器。 它是在Java 7中引入的,其最終目標是取代CMS GC。 它將堆劃分為多個大小相等的區域,然后執行GC,通常從實時數據較少的區域開始-因此,即“垃圾優先”。
最常見的內存不足問題
所有Java開發人員都應該知道的最常見的內存不足問題,以便正確地開始調試,如下所示:
- 線程“ main”中的異常:java.lang.OutOfMemoryError:Java堆空間這并不一定意味著內存泄漏,這可能是由于為堆配置的空間較小所致。 否則,在壽命長的應用程序中,可能是由于無意中提到了對堆對象的引用(內存泄漏)。 甚至應用程序調用的API都可能包含對不必要的對象的引用。 同樣,在過度使用終結器的應用程序中,有時對象會排隊進入終結隊列。 當這樣的應用程序創建更高優先級的線程并導致finalizaton隊列中的對象越來越多時,它可能會導致內存不足。
- 線程“ main”中的異常:java.lang.OutOfMemoryError:PermGen空間如果加載了許多類和方法,或者創建了很多字符串文字,尤其是通過使用intern()(從JDK 7開始,不再使用實習字符串) (PermGen的一部分)–然后會發生這種類型的錯誤。 發生這種錯誤時,文本ClassLoader.defineClass可能會出現在所打印的堆棧跟蹤頂部附近。
- 線程“ main”中的異常:java.lang.OutOfMemoryError:請求的數組大小超出VM限制當請求的數組大小大于可用堆大小時,再次發生這種情況。 如果為數組大小請求一個非常大的值,則通常可能是由于運行時的程序錯誤導致的。
- 線程“ main”中的異常:java.lang.OutOfMemoryError:請求<r>的<s>個字節。 交換空間不足?
通常這可能是內存泄漏的根本原因。 當操作系統沒有足夠的交換空間或另一個進程占用系統上所有可用的內存資源時,就會發生這種情況。 簡而言之,由于空間耗盡,它無法從堆中提供請求空間。 該消息指示失敗的請求的大小“ s”(以字節為單位)以及內存請求的原因“ r”。 在大多數情況下,消息的<r>部分是報告分配失敗的源模塊的名稱,盡管在某些情況下它表示原因。 - 線程“ main”中的異常:java.lang.OutOfMemoryError:<原因> <堆棧跟蹤>(本機方法)
這表明本機方法遇到分配失敗。 根本原因是該錯誤發生在JNI中,而不是在JVM內部執行的代碼中發生。 當本機代碼不檢查內存分配錯誤時,應用程序將崩潰而不是耗盡內存。
內存泄漏的定義
“將內存泄漏視為一種疾病,而將OutOfMemoryError視為一種癥狀。 但是,并非所有OutOfMemoryErrors都暗示內存泄漏,也不是所有內存泄漏都表現為OutOfMemoryErrors。 ”
在計算機科學中,內存泄漏是一種資源泄漏,當計算機程序錯誤地管理內存分配以致不再釋放不再需要的內存時,就會發生這種情況。 在面向對象的編程中 ,當對象存儲在內存中但無法被運行的代碼訪問時,可能會發生內存泄漏。
Java中內存泄漏的常見定義:
當不必要的對象引用被不必要地維護時,就會發生內存泄漏。
在Java中,內存泄漏是指某些對象不再被應用程序使用,但GC無法將其識別為未使用的情況。
當程序中不再使用某個對象,但仍在無法訪問的某個位置引用該對象時,將出現內存泄漏。 因此,垃圾收集器無法刪除它。 用于該對象的內存空間將不會釋放,并且用于程序的總內存將增加。 隨著時間的推移,這將降低性能,并且JVM可能會耗盡內存。
從某種意義上說,當在永久性空間上無法分配任何內存時,就會發生內存泄漏。
內存泄漏的一些最常見原因是:
我建議使用與JDK捆綁在一起的Visual VM,以開始調試內存泄漏問題。
內存泄漏的常見調試
調試內存泄漏問題的常用策略或步驟包括:
- 識別癥狀
- 啟用詳細垃圾回收
- 啟用分析
- 分析痕跡
祝幸福時光,解決Java內存問題!
翻譯自: https://www.javacodegeeks.com/2015/11/java-memory-architecture-model-garbage-collection-and-memory-leaks.html
js內存泄露 垃圾回收
總結
以上是生活随笔為你收集整理的js内存泄露 垃圾回收_Java内存体系结构(模型),垃圾回收和内存泄漏的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: linux链接库命令(linux链接库)
- 下一篇: jboss7.0.2_红帽JBoss企业