在Java中,數據類型可以分爲兩大種,Primitive Type(基本類型)和Reference Type(引用類型)。基本類型的數值不是對象,不能調用對象的toString()、hashCode()、getClass()、equals()等方法。所以Java提供了針對每種基本類型的包裝類型。如下:
那麼你可能會問Boolean佔多少字節呢?
雖然定義了boolean這種數據類型,但是隻對它提供了非常有限的支持。
在Java虛擬機中沒有任何供boolean值專用的字節碼指令,Java語言表達式所操作的boolean值,在編譯之後都使用Java虛擬機中的int數據類型來代替,而boolean數組將會被編碼成Java虛擬機的byte數組,每個元素boolean元素佔8位”。這樣我們可以得出boolean類型佔了單獨使用是4個字節,在數組中又是1個字節。使用int的原因是,對於當下32位的處理器(CPU)來說,一次處理數據是32位(這裏不是指的是32/64位系統,而是指CPU硬件層面),具有高效存取的特點。
Java 1.5提供了自動裝箱和拆箱的功能
裝箱:值類型——引用類型,系統會在託管堆中生成一份堆棧中值類型對象的副本。
拆箱:引用類型——值類型,從託管堆中將引用類型所指向的已裝箱數據複製會值類型對象。
<span style="font-size:18px;"><span style="font-family:Microsoft YaHei;font-size:14px;">lass Program
{
static void Main(string[] args)
{
//首先定義一個值類型
int i = 3;
//裝箱操作,因爲要往箱子裏裝,所以先分配好一塊內存來放這個數據也就是o
object o = i;
//拆箱操作
int y = (int)o;
}
} </span></span>
裝箱的操作分爲三步:
(1)內存分配:在託管堆中分配好內存空間以存放複製的實際數據。
(2)完成實際數據的複製:將值類型實例的實際數據複製到新分配的內存中。
(3)地址返回:將託管堆中的對象地址返回給引用類型變量。
但是拆箱和裝箱的操作對於系統性能是一次巨大的挑釁,因爲僅僅一個裝箱的操作就分了這麼多步驟,兩個過程都要進行數據的複製,一個系統要拆裝個好些回,還不得慢死啊。而且在這個過程中會產生多個不必要的對象,導致了系統性能的降低。所以爲了避免拆裝箱的操作,我們最好使用泛型來進行編程。但是有時候我們還是使用封裝類更方便。
既然提供了基本類型,爲什麼還要使用封裝類呢?
· 某些情況下,數據必須作爲對象出現,此時必須使用封裝類來將簡單類型封裝成對象。
1. 比如,如果想使用List來保存數值,由於List中只能添加對象,因此我們需要將數據封裝到封裝類中再加入List。在JDK5.0以後可以自動封包,可以簡寫成list.add(1)的形式,但添加的數據依然是封裝後的對象。
2. 另外,有些情況下,我們也會編寫諸如func(Object o)的這種方法,它可以接受所有類型的對象數據,但對於簡單數據類型,我們則必須使用封裝類的對象。
3. 某些情況下,使用封裝類使我們可以更加方便的操作數據。比如封裝類具有一些基本類型不具備的方法,比如valueOf(), toString(), 以及方便的返回各種類型數據的方法,如Integer的shortValue(), longValue(), intValue()等。
基本數據類型與其對應的封裝類由於本質的不同,具有一些區別:
· 基本數據類型只能按值傳遞,而封裝類按引用傳遞。
· 基本類型在堆棧中創建;而對於對象類型,對象在堆中創建,對象的引用在堆棧中創建。基本類型由於在堆棧中,效率會比較高,但是可能會存在內存泄漏的問題。