介绍

容器,就是可以容纳其他Java对象的对象
优点是:

  • 降低编程难度
  • 提高程序性能
  • 提高API间的互操作性
  • 降低学习难度
  • 降低设计和实现相关API的难度
  • 增加程序的重用性

Java容器里只能放对象,对于基本类型(int, long, float, double等),需要将其包装成对象类型后(Integer, Long, Float, Double等)才能放到容器里。很多时候拆包装和解包装能够自动完成。这虽然会导致额外的性能和空间开销,但简化了设计和编程

Collection

  1. 容器主要包括 Collection Map 两种,Collection 存储着对象的集合,而 Map 存储着键值对(两个对象)的映射表

Set

TreeSet

基于红黑树实现,支持有序性操作,例如根据一个范围查找元素的操作。但是查找效率不如 HashSet

HashSet

基于哈希表实现,支持快速查找,但不支持有序性操作

LinkedHashSet

具有 HashSet 的查找效率,且内部使用双向链表维护元素的插入顺序
LinkedHashSet里面有一个LinkedHashMap(适配器模式)
可将LinkedHashMap看作采用linked list增强的HashMap
事实上LinkedHashMap是HashMap的直接子类,二者唯一的区别是LinkedHashMap在HashMap的基础上,采用双向链表(doubly-linked list)的形式将所有entry连接起来,这样是为保证元素的迭代顺序跟插入顺序相同

List

ArrayList

ArrayList实现了List接口,是顺序容器,即元素存放的数据与放进去的顺序相同,允许放入null元素,底层通过数组实现

为追求效率,ArrayList没有实现同步(synchronized),如果需要多个线程并发访问,用户可以手动同步,也可使用Vector替代

自动扩容:
每当向数组中添加元素时,都要去检查添加后元素的个数是否会超出当前数组的长度,如果超出,数组将会进行扩容,以满足添加数据的需求
每次数组容量的增长大约是其原容量的1.5倍

Vector(外车)

和 ArrayList 类似,但它是线程安全的

LinkedList

底层数据结构:基于双向链表实现,只能顺序访问

LinkedList同时实现了List接口和Deque接口,也就是说它既可以看作一个顺序容器,又可以看作一个队列(Queue),同时又可以看作一个栈(Stack)

Queue(Q)

Queue接口继承自Collection接口,除了最基本的Collection的方法之外,它还支持额外的insertion, extractioninspection操作

LinkedList

可以用它来实现双向队列

PriorityQueue

概述
还有一种特殊的队列叫做PriorityQueue,即优先队列
优先队列的作用是能保证每次取出的元素都是队列中权值最小的

Map

TreeMap

TreeMap底层通过红黑树(Red-Black tree)实现
红黑树是一种近似平衡的二叉查找树,它能够确保任何一个节点的左右子树的高度差不会超过二者中较低那个的一陪
红黑树是满足如下条件的二叉查找树(binary search tree):

  1. 每个节点要么是红色,要么是黑色。
  2. 根节点必须是黑色
  3. 红色节点不能连续(也即是,红色节点的孩子和父亲都不能是红色)。
  4. 对于每个节点,从该点至null(树尾端)的任何路径,都含有相同个数的黑色节点

由于红黑树是一棵增强版的二叉查找树,红黑树的删除操作跟普通二叉查找树的删除操作也就非常相似,唯一的区别是红黑树在节点删除之后可能需要进行调整

HashMap

Java8 对 HashMap 进行了一些修改,最大的不同就是利用了红黑树,所以其由 数组+链表+红黑树 组成

HashMap实现了Map接口,即允许放入key为null的元素,也允许插入value为null的元素;除该类未实现同步外,其余跟Hashtable大致相同;跟TreeMap不同,该容器不保证元素顺序,根据需要该容器可能会对元素重新哈希,元素的顺序也会被重新打散,因此不同时间迭代同一个HashMap的顺序可能会不同

HashSet

HashSet是对HashMap的简单包装

HashTable

和 HashMap 类似,但它是线程安全的,这意味着同一时刻多个线程可以同时写入 HashTable 并且不会导致数据不一致

LinkedHashMap

使用双向链表来维护元素的顺序,顺序为插入顺序或者最近最少使用(LRU)顺序