自從上次咸菜給窩頭講解了算法的神奇后,窩頭就好像變了一個人,游戲不玩了,看見校園的妹紙也不回頭了,一門心思愛上了編程,這不昨天劉老師給布置了一項作業–了解java虛擬機(JVM)的內存分配。大清早就叫上學霸咸菜去了圖書館。 咸菜:“窩頭星期天,能不能省點心,這么早就叫我起來,人家昨天看了半夜的韓劇還沒睡醒呢!” 窩頭:“哎呀!咸菜,我好不容易準備洗心革面,好好學習,你就幫幫我吧!” 咸菜心想,這樣下去這孩子會不會學傻掉?都到圖書館了,看來今天是跑不掉了。 咸菜:“好吧,本姑娘見你迷途知返,就當一回司機,帶帶你” 窩頭心喜說道:“老司機就是穩!” 二人來到圖書館,二話沒說找到一個安靜的角落做了下來,咸菜從書包里 掏出一本書《深入理解JAVA虛擬機》對窩頭說:“給你,有時間看看吧” 窩頭:“咦!這是啥呢?” 咸菜說:“這本書講解了java在進行程序運行的時候JVM都做了什么,有助于呢理解java語言,不過這本書有點深奧,不急慢慢來” 咸菜又說:“今天就先給你講講一些比較淺顯的虛擬機內存的分配吧” 窩頭:”咸菜,你真厲害!“ 咸菜白了窩頭一眼說:“別拍馬屁,好好聽我說” 咸菜:“窩頭我問你?為什么java為什么這么流行?” 窩頭:“我知道,java語言具有良好的跨平臺性,可以在各大主流系統上運行” 咸菜:“那它又是怎么做到跨平臺的呢?” 窩頭:“這個我還真沒多想” 咸菜:“java之所以能夠跨平臺是以為存在JVM,java的程序是交給JVM來執行的,我給你畫個圖講解一下java執行的過程”
咸菜:“java源文件首先會被java編譯器編譯成java字節碼文件(.class文件),然后交給JVM中的類加載器加載類的字節碼文件,交給執行引擎去執行,JVM在執行的過程中會需要一段空間存放執行期需要的數據,這段空間就叫Runtime Data Aera(運行時數據)” 窩頭:“原來java是這樣保證跨平臺的啊,那么運行時數據區又是怎么進行java程序的數據處理的呢” 咸菜:“在java運行時數據的區域劃分,通常有如下幾塊: 程序計數器(PRogram Counter Register)、java堆棧(Stack)、java堆(Heap)、方法區(Method Area)、本地方法棧(Native Method Stack),如下圖:”
窩頭:“那么運行時數據區是怎么對數據進行操作的?” 咸菜:“ 1.程序計數器(Program Counter Register) 程序計數器是為了保證多線程在獲得CUP執行時間過程中,線程來回切換能夠保證線程能夠恢復到切換前的執行位置,就說明每個線程都有自己私有的程序計數器,就是用來指示執行哪條指令的。 2.java棧(Stack) 這個就厲害了,不要看它的空間不是太大,可是它的執行的速度是超快的,當然沒有CPU那么快拉,它主要用來存放局部變量(定義在函數中的變量包括:形參和函數中定義的非靜態變量)和基本數據類型,每當一個函數被調用的時候就會在棧中對應的創建一塊空間,它們遵循先進后出的原則,在函數使用完成后,java垃圾回收機制會將其自動清除棧,以防它占用空間(這就是以前跟你將的遞歸會導致內存溢出的原因)。 3.本地方法棧(Native Method Stack ) 它和上面的棧的功能其實是差不多的只不過,它服務的對象不是java程序而是本地方法,在HotSopt虛擬機中將棧和本地方法棧合二為一了。 4.堆(Heap) 堆是用來存放對象本身和數組的(數組的引用變量是自棧中),對象的實例變量是存放在堆上的(引用變量默認為null,整型默認為0,浮點型默認為0.0,布爾型默認為false),對象不再使用的時候會被java垃圾回收機制標記為特殊的記號,等待被回收,慘吧!對象的生命周期取決于程序員 窩頭:”對象好慘啊!“ 咸菜:”出個題考考你“ 窩頭:”好啊好啊“ 咸菜寫下代碼: 
咸菜:”窩頭,你說a等于幾?x[0]等于幾?“ 窩頭不屑的說:”這還不簡單,a=11,x[0]=1“ 咸菜:”你個豬頭,x[0]=8“ 窩頭:”弄啥呢?咋會等于8呢?“ 咸菜:”a和b是存放在棧中的但是數組的本身是存在堆上的,數組的引用是在棧上的,堆會給數組開辟一塊空間存放數組的元素,會返還給x一個地址,x就是通過地址操控數組的,當int[]y=x的時候,x就把指向數組的地址copy給y,這樣就說明名它們倆其實是指向同一個數組,當y對數組元素進行替換時,數組元素就被改變,所以在獲取數組元素的時候,得到的就是替換后的數據了。“ 窩頭:”這樣啊,下次可得小心了“ 咸菜:”除了上面四塊區域還有一塊區域叫方法區(Method Area),方法區在運行內存中還是挺重要的,在方法區中,存儲了類的名稱,函數的心信息,字段信息,靜態變量,常量和編譯后的代碼;在方法區中有一個部分是很重要的就是常量池。“ 窩頭:”常量池是干嘛的?咸菜“ 咸菜:”這個說起來話就多了,也是面試的時候面試官常考的點,找個時間給好好說說,它是在類或接口的常量池的運行是的表現形式,,在類和接口被加載到JVM后被創建出來,我們常說的常量池指運行時常量池“ 窩頭:”咸菜,為啥呢啥都知道呢?“ 咸菜:”哼,也不看看我是誰“ 未完待續...... 注:方法區和java堆是被所有線程共享的區域 參考資料:http://blog.csdn.net/u013510614/article/details/51896916?locationNum=5&fps=1
”
新聞熱點
疑難解答