如果一个程序只包含固定数量的且其生命期都是已知的对象,那么这是一个非常简单的程序。
1、泛型和类型安全的容器
- 使用Java SE5之前的容器的一个主要问题就是编译器允许你向容器中插入不正确的类型。
- 通过使用泛型,就可以在编译期防止将错误类型的对象放置到容器中,使用了泛型后从容器中取出元素不再需要强制转型。向上转型可以适用于泛型。
2、基本概念
Collection
- 一个独立元素的序列,这些元素都服从一条或多条规则。(List、Set、Queue)
Map(关联数组、字典)
- 一组成对的“键值对”对象,允许你使用键来查找值。
List
- List承诺可以将元素维护在特定的序列中。List接口在Collection的基础上添加了大量的方法,使得可以在List的中间插入和移除元素。
有两种List:
- ArrayList:**它长于随机访问元素,但是在List的中间插入和移除元素时较慢。
- LinkedList:**它通过代价较低的在List中间进行的插入和删除操作,提供了优化的顺序访问。LinkedList在随机访问方面相对比较慢,但是它的特性集较ArrayList更大。
迭代器
选代器(也是一种设计模式)是一个对象(也通常被称为轻量级对象:常见它的代价小),它的工作是遍历并选择序列中的对象,而客户端程序员不必知道或关心该序列底层的结构。
Iterator(只能单向移动):
1)使用方法iterator0要求容器返回一个Iterator。Iterator将准备好返回序列的第一个元素。
2)使用next0获得序列中的下一个元素。
3)使用hasNextO检查序列中是否还有元素。
4)使用remove0将迭代器新近返回的元素删除。
ListIterator是一个更加强大的Iterator的子类型,它只能用于各种List类的访问,并且可以双向移动。
LinkedList
- LinkedList也像ArrayList一样实现了基本的List接口,但是它执行某些操作(在List的中间插入和移除)时比ArrayList更高效,但在随机访问操作方面却要逊色一些。
- LinkedList相较于List还添加了可以使其用作栈、队列或双端队列的方法。
Stack
- “栈”通常是指“后进先出”(LIFO)的容器。有时栈也被称为叠加栈,因为最后“压入”栈的元素,第一个“弹出”栈。
- LinkedList具有能够直接实现栈的所有功能的方法,因此可以直接将LinkedList作为栈使用。
Set
- TreeSet将元素存储在红-黑树数据结构中(会自动排序)
- HashSet使用的是散列函数(元素顺序没有任何规律)
Map
- 将对象映射到其他对象的能力是一种解决编程问题的杀手铜。
- Map与数组和其他的Collection一样,可以很容易地扩展到多维,而我们只需将其值设置为Map(这些Map的值可以是其他容器,甚至是其他Map)。
Queue
队列是一个典型的**先进先出(FIFO)**的容器。即从容器的一端放入事物,从另一端取出,并且事物放入容器的顺序与取出的顺序是相同的。
LinkedList提供了方法以支持队列的行为,并且它实现了Queue接口,因此LinkedList可以用作Queue的一种实现(将LinkedList向上转型为Queue)。
PriorityQueue(优先级队列)
- 先进先出声明的是下一个元素应该是等待时间最长的元素。
- 优先级队列声明下一个弹出元素是最需要的元素(具有最高的优先级)。
生成Iterator是将队列与消费队列的方法连接在一起耦合度最小的方式,并且与实现Collection相比,它在序列类上所施加的约束也少得多。
Foreach与迭代器
- 与foreach一起工作是所有Collection对象的特性。
- 如果你创建了任何实现Iterable的类,都可以将它用于foreach语句中。
- JavaSE5中大量的类都是Iterable类型,主要包括所有的Collection类(但是不包括各种Map)。
- Arrays.asList()产生的List对象会使用底层数组作为其物理实现。只要你执行的操作会修改这个List,并且你不想原来的数组被修改,那么你就应该在另一个容器中创建一个副本,否则原数组会被修改。
3、总结
Java提供了大量持有对象的方式:
1)数组将数字与对象联系起来。它保存类型明确的对象,查询对象时,不需要对结果做类型转换。它可以是多维的,可以保存基本类型的数据。但是,数组一旦生成,其容量就不能改变。
2)Collection保存单一的元素,而Map保存相关联的键值对。有了Java的泛型,你就可以指定容器中存放的对象类型,因此你就不会将错误类型的对象放置到容器中,并且在从容器中获取元素时,不必进行类型转换。各种Collection和各种Map都可以在你向其中添加更多的元素时,自动调整其尺寸。容器不能持有基本类型,但是自动包装机制会仔细地执行基本类型到容器中所持有的包装器类型之间的双向转换。
3)像数组一样,List也建立数字索引与对象的关联,因此,数组和List都是排好序的容器,List能够自动扩充容量。
4)如果要进行大量的随机访问,就使用ArrayList;如果要经常从表中间插入或删除元素,则应该使用LinkedList。
5)各种Queue以及栈的行为,由LinkedList提供支持。
6)Map是一种将对象(而非数字)与对象相关联的设计。HashMap设计用来快速访问;而TreeMap保持“键”始终处于排序状态,所以没有HashMap快。LinkedHashMap保持元素插入的顺序,但是也通过散列提供了快速访问能力。
7)Set不接受重复元素。HashSet提供最快的查询速度,而TreeSet保持元素处于排序状态。
LinkedHashSet以插入顺序保存元素。
8)新程序中不应该使用过时的Vector、Hashtable和Stack。
java容器简图: