我以前對C++比較熟悉,所以就想當(dāng)然將C++中的數(shù)組與Java中的數(shù)組畫上了等號。讀過《TIJ》之后我發(fā)現(xiàn)并不是這么回事,所以,完全應(yīng)該重新認(rèn)識Java中的數(shù)組。這篇文章不是對Java中數(shù)組的全面介紹,只是我的一些心得。(有些內(nèi)容轉(zhuǎn)引自《TIJ》)
概論:
相對于C++中的數(shù)組,Java中的數(shù)組已經(jīng)有了很大的改進(jìn)。首先,Java中的數(shù)組是對象,這就意味著與C++中的數(shù)組的根本不同,相反,Java中的數(shù)組與C++中的STL或Java中的容器類反而更相像一些(只是作為對象,它的方法要比STL中的容器類或者Collection類少很多)。另外,Java中有支持?jǐn)?shù)組的一套算法,就像STL中的Algorithm與Java中的Collections類中的靜態(tài)方法一樣。當(dāng)然,嚴(yán)格的說,這些算法也許并不是STL和Collections類所強(qiáng)調(diào)的通用算法;但是它們是包含在標(biāo)準(zhǔn)庫中的高效的算法,對于程序員來說,這些算法可以不加修改的作用于各種不同類型的數(shù)組,也算是某種程度上的通用算法了。
下面主要從數(shù)組作為對象以及通用算法兩部分來討論Java數(shù)組區(qū)別于C++數(shù)組的特性。
1. Java中的數(shù)組作為對象帶來的好處
1.1 越界檢查
1.2 length field:與傳統(tǒng)的C++中的數(shù)組相比,length字段可以方便的得到數(shù)組的大??;但要注意,僅僅可以得到數(shù)組的大小,不能得到數(shù)組中實(shí)際包含多少個元素,因?yàn)閘ength 只會告訴我們最多可將多少元素置入那個數(shù)組。
1.3 初始化:對象數(shù)組在創(chuàng)建之初會自動初始化成null,由原始數(shù)據(jù)類型構(gòu)成的數(shù)組會自動初始化成零(針對數(shù)值類型),(Char)0 (針對字符類型)或者false (針對布爾類型)。
1.4 數(shù)組作為返回值:首先,既然數(shù)組是對象,那么就可以把這個對象作為返回值;而且,不必?fù)?dān)心那個數(shù)組的是否可用只要需要它就會自動存在而且垃圾收集器會在我們完成后自動將其清除
2. 通用算法
2.1 在java.util 中的Arrays 數(shù)組類容納著一系列靜態(tài)方法可簡化我們對數(shù)組的操作,總共有四個函數(shù)。equals()用于比較兩個數(shù)組是否相等、fill()可將一個值填入數(shù)組、sort()可對數(shù)組排序、而binarySearch()用于在排好序的數(shù)組中查找一個元素。所有這些方法都已為全部原始數(shù)據(jù)類型及對象重載使用。除此以外還有一個asList()方法可用它獲取任意數(shù)組然后把數(shù)組轉(zhuǎn)變成一個List 容器。
2.2 sort和binarySearch的使用:在Java 2 中有兩個辦法可提供比較功能。第一個辦法是用自然比較方法,這是通過實(shí)現(xiàn)java.lang.Comparable 接口來實(shí)現(xiàn)。Java 2 提供的第二個辦法來進(jìn)行對象的比較,單獨(dú)創(chuàng)建一個類實(shí)現(xiàn)名為Comparator 的一個接口。接口提供了兩個方法分別是compare()和equals() 。不過除非考慮到一些特殊的性能方面的因素,否則我們用不著實(shí)現(xiàn)equals() ,因?yàn)槊看蝿?chuàng)建一個類的時候它都會默認(rèn)從Object 繼承,而Object 已經(jīng)有了一個equals()。Comparator可以作為sort和binarySearch方法的參數(shù)。
3. 需要注意的問題
3.1 Java中的數(shù)組中既可以存儲基本的值類型,也可以存儲對象。對象數(shù)組和原始數(shù)據(jù)類型數(shù)組在使用方法上幾乎是完全一致的,唯一的差別在于對象數(shù)組容納的是引用而原始數(shù)據(jù)類型數(shù)組容納的是具體的數(shù)值。這一點(diǎn)要特別注意,在討論關(guān)于數(shù)組的問題時,一定要先確定數(shù)組中存儲的是基本值類型還是對象。特別是在調(diào)試程序時,要注意這方面。
例如:
Arrays提供了一個fill()方法將一個值復(fù)制到一個位置,如果是對象數(shù)組則將引用復(fù)制到每一個位置。
Java 標(biāo)準(zhǔn)庫提供了一個靜態(tài)方法名為System.arraycopy() 專門用于數(shù)組的復(fù)制它復(fù)制數(shù)組的速度比自己親自動手寫一個for 循環(huán)來復(fù)制快得多System.arraycopy()已進(jìn)行了重載可對所有類型進(jìn)行控制。無論原始數(shù)據(jù)類型數(shù)組還是對象數(shù)組我們都可對它們進(jìn)行復(fù)制。但是假如復(fù)制的對象數(shù)組,那么真正復(fù)制的只是引用對象本身可不會復(fù)制。
3.2 為什么使用數(shù)組而不使用ArrayList等容器類?
效率和類型。
3.2.1 效率:
對于Java 來說要想保存和隨機(jī)訪問一系列對象實(shí)際是對象引用效率最高的方法莫過于數(shù)組。
3.2.2 類型:
Java標(biāo)準(zhǔn)庫中的容器類都把對象當(dāng)作沒有具體類型那樣對待,換言之它們將其當(dāng)作Object 類型處理。Object 類型是Java 中所有類的根類,從某種角度看這種處理方法是非常合理的,我們只需構(gòu)建一個容器然后所有Java 對象都可進(jìn)入那個容器。原始數(shù)據(jù)類型除外,可用Java 的基類型封裝器類將其作為常數(shù)置入容器或自建一個類把它們封裝到里面當(dāng)作可變值進(jìn)行對待。這再一次體現(xiàn)出數(shù)組相較于普通容器的優(yōu)越性,創(chuàng)建一個數(shù)組時可讓它容納一種特定的類型。這意味著可進(jìn)行編譯時間的類型檢查防范自己設(shè)置了錯誤的類型或者錯誤地提取了一種類型,而不是運(yùn)行時的Exception。
總結(jié):在你想容納一組對象的時候第一個也是最有效的一個選擇便是數(shù)組。