Java程序爲了提升程序的效率,就對數據進行了不一樣空間的分配,具體以下:java
1.棧:存放的是局部變量;c++
2.堆:存放的是全部new出來的東西;程序員
3.方法區:(面向對象的東西)數組
4.本地方法區:存放的是和系統相關的東西,好比Windows、Linux。多線程
5.寄存器:CPU使用的。jvm
如下着重介紹堆和棧!函數
棧(stack)和堆(heap)都是JAVA在RAM中存放數據的地方。spa
*與C++不一樣,JAVA自動管理棧和堆,程序員不能直接的設置棧和堆。線程
棧內存:指針
存儲的都是局部變量,並且變量所屬的做用域一旦結束,該變量就自動釋放。
堆內存:
存儲的是數組和對象(其實數組也是對象),凡是new創建在堆中。
特色:1.每個實體都有首地址值;
2.堆內存中的每個變量都有默認初始化值,根據類型的不一樣而不一樣;
棧和堆在內存中的存儲方式可參考下圖:
舉例:int[] arr = new int[3];
步驟:
1,建立變量arr,且這個局部變量在主函數中,故主函數的代碼段先進棧;
2,右邊用new創建的對象是實體,故放在堆中;
3,給該對象分配一個內存地址,用來存放該對象,好比:0x0045;(堆會對其中的對象進行默認初始化)
4,將對象的地址0x0045賦給棧中的變量arr,而arr就指向堆中的這個地址(也能夠做稱做引用這個地址),相似於c++中的指針。
棧的優點:存取速度比堆要快,僅次於直接位於CPU中的寄存器。
棧的缺點:1.存在棧中的數據大小和生存期必須是肯定的,缺少靈活性。
2.棧數據在多個線程或者多個棧之間是不能夠共享的。(可是,在棧內部多個值相等的變量是能夠指向一個地址的)
堆的優點:能夠動態的分配內存大小,生存期也沒必要事先告訴編譯器,JAVA的垃圾收集器會自動收走不用的數據。
堆的缺點:因爲要在運行時動態分配內存,存取速度較慢。
JAVA中的數據類型有兩種:
一.基本類型(byte,short,int,long,float,double,boolean,char)
這種類型定義的變量被稱做自動變量,自動變量存的是字面值,不是類的實例(即不是類的引用)。
好比:int a=3,long b=255L 這些字面值的數據,因爲大小可知,生存期可知,出於追求速度的緣由,就存在於棧中。
二.包裝類數據(如Integer,String,Double等將相應的基本數據類型包裝起來的類,這些類數據所有存在於堆中)
JAVA用new語句來顯式的告訴編譯器,在運行時才根據須要動態建立,所以比較靈活,但缺點是要佔用更多的時間。
注意:包裝類的值不可修改!
--------------------------------------------------------------------------------------------------------------------------------------------
由上圖1可知,JVM的基本結構包括:類裝載器,內存區域,執行引擎,本地庫接口。
下面主要介紹一下內存區:
1.虛擬機棧
每當啓動一個新線程的時候,java虛擬機都會爲它分配一個java棧,故每一個線程包含一個棧區。
每一個棧中的數據都是私有的,其它棧不能訪問。棧分爲3個部分:基本類型變量區、執行環境上下文、操做指令區。
2.堆內存
存儲的所有是對象,每一個對象包含一個與之對應的class信息-----class的目的是獲得操做指令。
jvm只有一個堆區被全部線程共享,堆區中不存放基本類型和對象引用,只存放對象自己。
3.方法區
在方法區中,存儲了每一個類的信息(包括類的名稱、方法、字段)、靜態變量、常量以及編譯器編譯後的代碼等。
4.本地方法棧
和虛擬機棧的做用差很少,只不過是爲JVM使用到的native方法服務的。
*.在HotSopt虛擬機中直接就把本地方法棧和虛擬機棧合二爲一了。
5.程序計數器
用於保存當前線程執行的內存地址。
因爲JVM程序是多線程執行的,爲了保證線程切換回來後,還能恢復到原先狀態,就須要一個獨立的計數器,記錄以前中斷的地方,可見程序計數器也是線程私有的。