1. 程式人生 > >從ArrayList看Java泛型

從ArrayList看Java泛型

ArrayListJava泛型

一、知識點

1、Java 泛型

2、Java 多型

3、Java ArrayList原始碼

二、個人理解

1、泛型更形式面向物件思想多型的擴充套件,它的使用範圍更多的針對於類型別的引數、方法引數、方法返回值等等,它可以讓程式的程式碼更簡潔、減少你程式裡面因為型別不匹配,在進行顯示轉換的時候,導致的型別強制轉換錯誤。說泛型是“通配”作用,我更喜歡用“限定範圍”這個詞來描述Java泛型的妙用,注意Java的泛型是在JDK1.5之後引入的,不過目前這個都升級到1.8了,還有人用1.5麼。。。

2、在Java中泛型的使用,最常用的應該是集合型別Collection下的子類。例如ArrayList;下面我們進入到ArrayList原始碼中來檢視其中是如何利用Java泛型的。

<1>知識點:Java的泛型作用範圍主要是Class、Fouction、Params、Var等等。例如ArrayList中:

(1)作用於類:public class ArrayList<E> extends AbstractList<E>

(2)作用於方法:public E get(int index)/

                        public  ArrayList(Collection<? extends E> c)(構造方法)

(3)作用於引數:public <T> T[] toArray(T[] a)

(4)作用於變數的在這沒有具體體現,但是跟引數的樣子類似

NOTE:這裡的E和T都是一種泛型的型別名稱,代表的是一種類型別(不可以基本資料型別哦),可以是任意符合JAVA命名規範的,通常用單個字元標示根據代表性。

<2>知識點:萬用字元,相比大家都注意到了上面作用於方法中的那個構造方法中的?吧,沒錯這就是萬用字元,在構造方法裡面的作用是用來初始化ArrayList方法,限定的範圍是包含E型別(含子類)的Collection物件,在ArrayList的類物件限制中E並沒有明確指出限制條件,其父類也未曾有任何限制,則預設E的範圍是Object型別。這下你就可以理解ArrayList<String>\ArrayList<Integer>等等的限定作用了吧。因為泛型是執行時判斷的,所以編譯時所有的新增操作都是不允許的,因為編譯時候,虛擬機器無法確定你新增的內容和已有集合的資料型別一致,所以預設情況下使用萬用字元虛擬機器只允許你從內容裡面讀取,但是我們使用ArrayList的時候增刪改查都可以使用呀,這是什麼原因呀,這是我查到的總結的比較好的萬用字元使用方法,直接搬過來吧:

<!--[if !supportLists]-->l         <!--[endif]-->如果你想從一個數據型別裡獲取資料,使用 ? extends 萬用字元

<!--[if !supportLists]-->l         <!--[endif]-->如果你想把物件寫入一個數據結構裡,使用 ? super 萬用字元

<!--[if !supportLists]-->l         <!--[endif]-->如果你既想存,又想取,那就別用萬用字元。

<3>上面所說的限定會引出今天的第三個知識點,範圍的限定:向上限定向下限定。向上限定 ? Super ClassName、向下限定 extends和&符號。

三、擴充套件

<1>不知道大家注意到上面的ArrayList裡面這個物件陣列了沒。

/**

     * The array buffer into which the elements of the ArrayList are stored.

     * The capacity of the ArrayList is the length of this array buffer. Any

     * empty ArrayList with elementData == EMPTY_ELEMENTDATA will be expanded to

     * DEFAULT_CAPACITY when the first element is added.

     */

private transient Object[] elementData;

這個物件數組裡面儲存的就是我們存放到數組裡的String、Integer等等物件,最終都會轉換當做物件存放在該陣列內,這個就是核心裝換方法,增刪改查都需要該方法的處理,看到他做了什麼事情麼對的沒錯他做了強制轉換:  

  // Positional Access Operations

    @SuppressWarnings("unchecked")

    E elementData(int index) {

        return (E) elementData[index];

    }

四、總結

<1>泛型是減少程式碼提高相容性的利器,執行時決定製定的型別,很有幫助,最近正在封裝一個Android網路請求類,會將泛型新增到裡面,到時再講程式碼新增關聯過去吧。

<2>關於Java泛型可查閱的連結: