(1)Java集合框架
Java最初版本只为最常用的数据结构提供了很少的一组类:Verctor、Stack、Hashtable、BitSet与Enumeration接口,其中Enumeration接口提供了一种用于访问任意容器中各个元素的抽象机制。这是一种很明智的选择,但想要建立一个全面的集合类库还需要大量的时间。
-
将集合的接口与实现分离
与现代的数据结构类库的常见情况一样,Java集合类库也将接口与实现分离。例如,队列:
队列接口可以在队列的尾部添加元素,在队列的头部删除元素,并且可以查找队列中元素的个数。当需要收集对象,并按照“先进先出”的规则检索对象时就应该使用队列。
队列接口的最简单形式可能类似下面这样:public interface Queue<E> { void add(E element); E remove(); int size(); }
这个接口并没有说明队列时如何实现的。队列通常有两种实现方式:一种是使用循环数组;另一种是使用链表。
每个实现都可以通过一个实现了Queue接口的类表示。public class CircularArrayQueue<E> implements Queue<E> { private int head; private int tail; CircularArrayQueue(int capacity){ //... } public void add(E element) { //... } public E remove(){ //... } public int size() { //... } private E[] elements; } public class LinkedListQueue<E> implements Queue<E> { private Link head; private Link tail; LinkedListQueue() { //... } public void add(E element) { //... } public E remove() { //... } public int size() { //... } }
实际上,Java类库没有名为CircularArrayQueue和LinkedListQueue的类。这里,只是以这些类作为示例,解释一下集合接口与实现在概念上的不同。如果需要一个循环数组队列,就可以使用ArrayDequeue类。如果需要一个链表队列,就直接使用LinkedList类,这个类实现了Queue接口。
当程序中使用队列时,一旦构建了集合就不需要知道究竟使用了哪种实现。因此,只有在构建集合对象时,使用具体的类才有意义。可以使用接口类存放集合的引用。Queue<Customer> expressLane = new CircularArrayQueue<>(100); experssLane.add(new Customer("Harry"));
利用这种方式,一旦改变了想法,可以轻松的使用另外一种不同的实现。只需要对程序的一个地方做出修改,既调用构造器的地方:
Queue<Customer> expressLane = new LinkedListQueue<>(); expressLane.add(new Customer("Harry"));
-
Collection接口
在Java类库中,集合类的基本接口是Collection接口。这个接口有两个基本方法:public interface Collection<E> { boolean add(E element); Iterator<E> iterator(); //... }
add方法用于向集合中添加元素。如果添加元素确实改变了集合就返回true,否则就返回false。
iterator方法用于返回一个实现了Iterator接口的对象。可以使用这个迭代器对象依次访问集合中的元素 -
迭代器
Iterator接口包含4个方法:
public interface Iterator {
E next();
booleam hasNext();
void remove();
default void forEachRemaining(Consumer<? super E> action);
}