聲明:
Author:趙志乾
Date:2018-6-18
Declaration:All Right Reserved!!!
背景知識:
[java虛拟機]--(1)java記憶體區域--(1)線程私有區域
虛拟機記憶體之線程間共享區域:
1、堆
談及記憶體區域的劃分,一般會将記憶體區域簡單的劃分為堆記憶體和棧記憶體。當然,這隻是一種粗粒度的劃分,詳細的劃分見《java記憶體區域》。對于開發而言,堆記憶體相較于棧記憶體,其生命周期更具可管理性。因為棧是依據線程調用層級自行建構的,開發人員在這一過程中,并沒有對棧記憶體進行管控的機會。每個棧幀的生命周期都是始于對應方法的調用、止于方法的結束。而堆記憶體的配置設定和回收權限在不同的應用中,則有不同的規定:
C++應用:堆記憶體的配置設定和回收完全由開發人員來控制。遵循“誰申請、誰釋放,誰建立、誰銷毀”的原則。這也是C++應用中容易出現記憶體洩漏的原因。
Java應用:堆記憶體的配置設定由開發人員控制,而回收則由虛拟機來控制。虛拟機能夠依據堆記憶體的使用情況進行批次回收,進而降低應用中記憶體洩漏的風險。
虛拟機中的堆記憶體是各區域中占比最大的一塊,也是gc線程回收記憶體的重點區域。當堆記憶體占滿,無法做進一步申請時,會抛出OutOfMemoryError異常。由于堆記憶體為線程間共享,是以使用堆記憶體可以很友善的實作線程間的通信,也因其為多線程操作,并發通路時需要開發人員保證共享區域的線程安全性。
注:堆記憶體是虛拟機規範中唯一用于存放對象執行個體的區域,但在虛拟機的具體實作中,這一描述并不準确。
2、方法區
方法區的概念源于CPU所管理記憶體中的代碼段。在馮諾伊曼架構體系中,代碼和資料分開存儲,CPU會分别從代碼段取得指令、資料段取得操作數進行計算。虛拟機規範中,則将代碼段的概念遷移到方法區。
方法區雖源于代碼段,但在虛拟機中,其方法區存儲的内容不止代碼。還包括靜态變量、常量、類資訊等等。其中最為出名的就是運作時常量池。
運作時常量池會存放位元組碼檔案中的常量池内容,也包括在類加載階段翻譯出來的直接引用。其相較于檔案中的常量池,最大的特點就是具有動态行,即應用運作期間會有新的常量加入運作時常量池。運作時常量池中的内容也會由gc線程進行回收,但不是強制要求(因為對于整個方法區而言,gc效果并不顯著)。故在不同的虛拟機實作中,實作的機制也大不相同。
注:因為方法區在應用運作期間,會有内容不斷的加入。是以當沒有記憶體可用時,其也會抛出OutOfMemoryError異常。
郵箱:[email protected]
參考資料:《深入了解java虛拟機》--周志明