前言
ArrayList 是 Java 串列 (List) 的其中一種實作。ArrayList
內部是動態陣列 (dynamic array)。由於 Java 不支援運算子重載 (operator overloading),ArrayList
無法用 [...]
存取元素。
建立 ArrayList 物件
在預設情形下,Java 不會自動引入 ArrayList
。要使用該容器的話,請引入以下物件:
import java.util.ArrayList;
import java.util.List;
使用以下敘述在建立 ArrayList
物件:
List<Integer> lst = new ArrayList<Integer>();
建立 ArrayList
物件的方式為使用 new
保留字,這和先前建立陣列雷同。
此處建立 ArrayList
物件,但是把變數 lst
的資料型態標註為 List
,因為我們只需要 List
提供的公開方法 (public method)。
<...>
是泛型程式設計 (generic programming) 的語法。該範式將資料型態參數化,但 Java 的泛型不能用基礎型態,故此處填入 Integer。
如果需要使用 ArrayList
特有的公開方法,則改用以下敘述:
ArrayList<Integer> lst = new ArrayList<Integer>();
由於 Java 泛型程式不支援基礎型態,以下敘述是錯的:
/* WRONG CODE. */
List<int> lst = new ArrayList<int>();
存取 ArrayList 物件的元素
中由於 Java 不支援運算子重載,無法使用 [...]
存取元素。替代的方式是用 get() 函式取得元素,使用 add(E) 函式從尾端新增元素。參考以下範例:
import java.util.ArrayList;
import java.util.List;
public class MainProgram
{
public static void main (String[] args)
{
/* Create a ArrayList object. */
List<Integer> lst = new ArrayList<Integer>();
/* Some integer data. */
int data[] = {1, 2, 3, 4, 5};
for (int n : data) {
/* Append an element to
the rear of the list. */
lst.add(n);
}
/* Retrieve an element from the list. */
assertCond(5 == lst.get(4));
}
/* Home-made assert. */
public static void assertCond (boolean cond)
{
if (!cond)
throw new IllegalArgumentException("Wrong condition");
}
}
女如果要在指定位置新增元素,則改用 add(i, E) 函式。這兩個函式是同名的,這項特性稱為函式重載 (function overloading):
for (int i = 0; i < data.length; ++i) {
/* Add an element to a specific location
of the list. */
lst.add(i, data[i]);
}
add(i, E)
函式的 i
必需要介於 0
和容器寬度 (不包含) 之間,否則會拋出 IndexOutOfBoundsException 例外。
注意 set(i, E) 函式無法增長 ArrayList
寬度。故以下程式碼會引發錯誤:
for (int i = 0; i < data.length; ++i) {
/* WRONG CODE. */
lst.set(i, data[i]);
}
檢查特定元素是否存在
使用 contains() 函式來檢查特定元素是否存在。參考以下範例:
import java.util.ArrayList;
import java.util.List;
public class MainProgram
{
public static void main (String[] args)
{
List<Integer> lst = new ArrayList<Integer>();
int data[] = {1, 2, 3, 4, 5};
for (int n : data)
lst.add(n);
/* Check whether an element exists. */
assertCond(lst.contains(5));
}
/* Home-made assert. */
public static void assertCond (boolean cond)
{
if (!cond)
throw new IllegalArgumentException("Wrong condition");
}
}
走訪 ArrayList 物件
使用計數器 (Counter)
ArrayList
在本質上是陣列,當然可以用計數器來走訪:
for (int i = 0; i < lst.size(); ++i)
System.out.println(lst.get(i));
可以使用計數器的前提是程式設計者知道 ArrayList
以非負整數為索引,每次遞增 1
。不一定每種容器都能使用計數器。
使用隱式迭代器 (Implicit Iterator)
ArrayList
內部隱藏迭代器,故以下程式碼是合理的:
for (int n : lst)
System.out.println(n);
另外可以注意到此處變數 n
的資料型態是 int
而非 Integer
,這裡用到了 Java 的自動型態轉換。手動在基礎型態和其相關類別間轉換的程式碼太繁瑣了,所以 Java 自動完成這些細部過程。
使用顯式迭代器 (Explicit Iterator)
既然有隱式迭代器可用,也可以直接提出顯式迭代器來用。參考以下範例:
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
public class MainProgram
{
public static void main (String[] args)
{
List<Integer> lst = new ArrayList<Integer>();
int data[] = {1, 2, 3, 4, 5};
for (int n : data)
lst.add(n);
Iterator<Integer> it = lst.iterator();
while (it.hasNext()) {
int n = it.next();
System.out.println(n);
}
}
}
此處的程式碼和前一小節的 for
迴圈是等效的,但寫起來比較長。所以這樣的模式是不必要的,本小節範例僅供參考。