商城網(wǎng)站建設(shè)預(yù)算免費網(wǎng)頁制作網(wǎng)站
一、產(chǎn)生背景
由于跨平臺性的設(shè)計,Java的指令都是根據(jù)棧來設(shè)計的,不同平臺的CPU架構(gòu)不同,所以不能設(shè)計為基于寄存器的。
二、概述
????????棧也叫棧內(nèi)存,主管Java程序的運行,是在線程創(chuàng)建時創(chuàng)建,線程銷毀時銷毀,它的生命周期是跟隨線程的生命周期,線程結(jié)束,棧內(nèi)存也就釋放,對于棧來說不存在垃圾回收,只要線程一結(jié)束該棧就over,生命周期和線程一致,是線程私有的。8種基本類型的變量+對象的引用變量+實例方法都是在函數(shù)的棧內(nèi)存中分配。
三、特點
(1)棧是一種快速有效的分配存儲方式,訪問速度僅次于程序計數(shù)器;
(2)JVM直接對Java棧的操作只有2個,即:
? ? ? ? a、每個方法執(zhí)行,伴隨著進(jìn)棧、出棧操作;
? ? ? ? b、方法結(jié)束后,執(zhí)行出棧操作;
(3)對于棧來說,不存在垃圾回收工作;
四、棧中存什么
8中基本數(shù)據(jù)類型 + 對象的引用變量 + 實例方法。
byte、short、int、long、float、double、boolean、char
五、棧幀中存什么
棧中主要保存3種數(shù)據(jù),即:
????????本地變量(Local Variables):輸入?yún)?shù)和輸出參數(shù),以及方法內(nèi)的變量;
????????棧操作(Operand Stack):記錄出棧、入棧的操作;
????????棧幀數(shù)據(jù)(Frame Data):包括類文件、方法等
備注:java中的方法進(jìn)入虛擬機(jī)后叫做棧幀。
六、棧的運行原理
?????????棧中的數(shù)據(jù)都是以棧幀(Stack Frame)的格式存在,棧幀是一個內(nèi)存區(qū)塊,是一個數(shù)據(jù)集,是一個有關(guān)方法(Method)和運行期數(shù)據(jù)的數(shù)據(jù)集,當(dāng)一個方法A被調(diào)用時就產(chǎn)生了一個棧幀 F1,并被壓入到棧中,A方法又調(diào)用了 B方法,于是產(chǎn)生棧幀 F2 也被壓入棧,B方法又調(diào)用了 C方法,于是產(chǎn)生棧幀 F3 也被壓入棧,……執(zhí)行完畢后,先彈出F3棧幀,再彈出F2棧幀,再彈出F1棧幀……遵循“先進(jìn)后出”/“后進(jìn)先出”原則。每個方法執(zhí)行的同時都會創(chuàng)建一個棧幀,用于存儲局部變量表、操作數(shù)棧、動態(tài)鏈接、方法出口等信息,每一個方法從調(diào)用直至執(zhí)行完畢的過程,就對應(yīng)著一個棧幀在虛擬機(jī)中入棧到出棧的過程。棧的大小和具體JVM的實現(xiàn)有關(guān),通常在256K~756K之間,約等于1MB左右。
七、棧中常見的異常 & 如何設(shè)置棧大小
7.1、概述
????????Java虛擬機(jī)規(guī)范允許Java棧的大小是動態(tài)的或者固定不變;
? ? ? ? 如果采用固定大小的Java虛擬機(jī)棧,那每一個線程的Java虛擬機(jī)棧容量可以在線程創(chuàng)建時獨立選定,如果線程請求分配的棧容量超過Java虛擬機(jī)棧允許的最大容量,將會拋出異常
StackOverflowError異常;
? ? ? ? 如果Java虛擬機(jī)棧可以動態(tài)擴(kuò)展,并且在嘗試擴(kuò)展時無法申請到足夠的內(nèi)存,或者在創(chuàng)建新的線程時沒有足夠的內(nèi)存去創(chuàng)建對應(yīng)的虛擬機(jī)棧,那么Java虛擬機(jī)將拋出異常
OutOfMemoryError異常(是一個錯誤);
7.2、默認(rèn)情況下棧的大小
/*** @Author : 一葉浮萍?xì)w大海* @Date: 2023/11/16 18:55* @Description: 默認(rèn)情況下棧的大小*/
public class StackMainApp {private int stackLength = 1;public void stackLeak() {stackLength++;stackLeak();}public static void main(String[] args) {StackMainApp stackMainApp = new StackMainApp();try {stackMainApp.stackLeak();} catch (Throwable e) {System.out.println("stackLength = " + stackMainApp.stackLength);e.printStackTrace();}}}
7.3、修改棧的大小
-Xss128k