1. 程式人生 > >Java資料型別和不同資料型別在JVM記憶體分配

Java資料型別和不同資料型別在JVM記憶體分配

1.java資料型別分類

       Java語言是強型別(Strongly typed)語言,強型別包含兩方面的含義:①所有的變數必須先宣告,後使用;②指定型別的變數只能接受型別與之匹配的值。這意味著每個變數和每個表示式都有一個在編譯時就確定的型別。

       Java語言支援的型別有兩類:基本型別(Primitive Type)和引用型別(Reference Type)。基本型別包括boolean型別和數值型別。數值型別有整數型別和浮點型別。整數型別包括byte、short、int、long、char,浮點型別包括float和double。引用型別包括類,介面和陣列型別,還有一種特殊的null型別。所謂引用型別就是對一個物件的引用,物件包括例項和陣列兩種。實際上引用型別變數就是一個指標,只是java語言不在使用指標這個說法。空型別(null type)就是null值的型別,這種型別沒有名稱,所以不可能宣告一個null型別的變數或者轉換到null型別。空引用(null)是null型別變數唯一的值。空引用可以轉換為任何引用型別。在實際開發中,程式設計師可以忽略null型別,假定null只是引用型別的一個特殊直接量。(注:空引用null只能被轉換為引用型別,不能轉換為基本型別,因此不要把null賦給一個基本型別的變數)

       宣告變數的語法:type varName[=初始值];

2.java不同資料型別在JVM中記憶體的存放位置

       變數在JVM中記憶體的分配主要取決於變數的作用範圍與變數的資料型別。

       基本資料型別是放在棧中還是放在堆中,這取決於基本型別在何處宣告,下面對資料型別在記憶體中的儲存問題來解釋一下:

        2.1.在方法中宣告的變數,即該變數是區域性變數,每當程式呼叫方法時,系統都會為該方法建立一個方法棧,其所在方法中宣告的變數就放在方法棧中,當方法結束系統會釋放方法棧,其對應在該方法中宣告的變數隨著棧的銷燬而結束,這就區域性變數只能在方法中有效的原因。在方法中宣告的變數可以是基本型別的變數,也可以是引用型別的變數。

         (1)當宣告是基本型別的變數的時,其變數名及值(變數名及值是兩個概念)是放在JAVA虛擬機器棧中

         (2)當宣告的是引用變數時,所宣告的變數(該變數實際上是在方法中儲存的是記憶體地址值)是放在JAVA虛擬機器的棧中,該變數所指向的物件是放在堆類存中的。

       2.2.在類中宣告的變數是成員變數,也叫全域性變數,放在堆中的(因為全域性變數不會隨著某個方法執行結束而銷燬)。

       同樣在類中宣告的變數即可是基本型別的變數 也可是引用型別的變數

       (1)當宣告的是基本型別的變數其變數名及其值放在堆記憶體中的

       (2)引用型別時,其宣告的變數仍然會儲存一個記憶體地址值,該記憶體地址值指向所引用的物件。引用變數名和對應的物件仍然儲存在相應的堆中。

3.Java不同資料型別在JVM中何時分配記憶體

      3.1.成員變數:

      當系統載入類或建立類的例項時,系統會自動為成員變數分配記憶體空間,並在分配記憶體空間後自動為成員變數指定初始值。基本資料型別預設初始值是0,引用資料型別預設初始值是null。

     3.2.區域性變數:

      區域性變數定義後,必須經過顯示初始化後才能使用。這意味著定義了局部變數後,系統並未為這個變數分配記憶體空間,直到等到程式為這個變數賦值初始值時,系統才會給區域性變數分配記憶體,並將初始值儲存在這塊記憶體中。

     與成員變數不同,區域性變數不屬於任何類或例項,因此它總是儲存在其所在方法的棧記憶體中。如果區域性變數時基本型別變數,則直接把變數值存在棧中,如果是引用型別,則存放地址在棧中。

     棧記憶體中的變數無須系統垃圾回收,變數是隨方法或程式碼塊的執行結束而結束的。因此,區域性變數的作用域是從初始化該變數開始,直到該方法或該程式碼塊執行完成而結束。因為區域性變數只儲存基本型別的值或物件的引用,因此區域性變數所佔的記憶體通常較小。

     當我們定義一個成員變數時,成員變數將被放置到堆記憶體中,成員變數的作用域將擴大到類存在範圍或者物件存在範圍。這種範圍擴大有兩個壞處:

     ①增大了變數的生存時間,將導致更大的系統開銷

     ②擴大了作用域,不利於程式的內聚性。