List ADT(Abstract Data Type:抽象数据类型)
在编程语言中 List 是类库中的一个类,可以简单视之为双向连结串行,以线性列的方式管理物件集合。list 的特色是在集合的任何位置增加或删除元素都很快,但是不支持随机存取。list 是类库提供的众多容器(container)之一,除此之外还有 vector、set、map 等。List 以模板方式实现(即泛型),可以处理任意型别的变量,包括使用者自定义的资料型态。
List ADT 有两种流行的实现方式,数组实现及链表实现,在 java 中对应的是 ArrayList 和 LinkedList。ArrayList 类提供了 List ADT 的一种变长数组的实现,优点在于对 get 和 set 的调用花费常数时间,缺点是新项插入及删除代价高(除了在末端发生变动的情况);LinkedLIst 类则提供了 List ADT 的双链表实现,优点在于,当新项的插入及删除位置已知的情况下开销都很小,即在 List 的前端及末端进行变动都是花销常数时间,缺点是它不容易做索引,因此对与 get 的调用花销时间长(如果 get 项不在端点附近)。
ArrayList 类简单实现
这里开发 SimpleArrayList 类来简单实现 ArrayList 功能,此类将提供一种机制改变数组容量,允许虚拟机回收老数组,提供 get、set、add、sort 等方法,提供一个内部类 SimpleItr 实现 Iterator 接口的 next、hasNext 等函数,在此基础上再提供原 ArrayList 没有的 adds 方法,代码如下所示:
import java.util.Arrays;
import java.util.Comparator;
import java.util.Iterator;
import java.util.NoSuchElementException;
/**
* ArrayList 简单实现</p>
* 1. 提供一种机制以改变数组容量,允许虚拟机回收老数组</p>
* 2. 提供 get、set、size、isEmpty、 clear、remove 和 add 等方法</p>
* 3. 提供一个类实现 Iterator 接口,实现 next、hasNext 等</p>
* 4. 提供一个sort排序方法,自实现比较规则</p>
* 5. 提供 adds 方法实现单次输入多参数</p>
*
* @author floyd
*/
public class SimpleArrayList<T> implements Iterable<T> {
private static final int DEFAULT_CAPACITY = 10;
private int size;
private Object[] element;
// 创建时初始化
public SimpleArrayList() {
clear();
}
public void clear() {
size = 0;
ensureCapacity(DEFAULT_CAPACITY);
}
public int size() {
return size;
}
public boolean isEmpty() {
return size == 0;
}
// 修剪空间
public void trimToSize() {
ensureCapacity(size());
}
@SuppressWarnings("unchecked")
T element(int index) {
return (T) element[index];
}
public T get(int i) {
// 检查数组是否越界
rangeCheck(i);
return element(i);
}
public T set(int i, T newVal) {
rangeCheck(i);
T oldVal = element(i);
element[i] = newVal;
return oldVal;
}
private void rangeCheck(int index) {
if (index >= size)
throw new ArrayIndexOutOfBoundsException();
}
private void rangeCheckForAdd(int index) {
if (index > size || index < 0)
throw new ArrayIndexOutOfBoundsException();
}
public void ensureCapacity(int newCapacity) {
if (newCapacity < size) return;
Object[] oldElement = element;
element = new Object[newCapacity];
for (int i = 0; i < size; i++) {
element[i] = oldElement[i];
}
}
public boolean add(T e) {
add(size, e);
return true;
}
// 实现一次性添加多个元素 “...” 表示变长参数
@SuppressWarnings("unchecked")
public boolean adds(T... ee) {
for (int i = 0; i < ee.length; i++)
add(size, ee[i]);
return true;
}
public void add(int index, T e) {
rangeCheckForAdd