容器主要包括Collection和Map两种,Collection存储着对象的集合,而Map存储着键值对(两个对象)的映射表。
- Collection
-
Set
-
TreeSet
TreeSet是对TreeMap的简单包装,对TreeSet的函数调用东环转换成合适的TreeMap方法。
-
HashSet
HashSet是对HashMap的简单包装,对HashSet的函数调用都会转换成合适的HashMap方法。
-
LinkedHashSet
LinkedHashSet是对LinkedMap的简单包装,对LinkedHashSet的函数调用都会转换成合适的LinkedHashMap方法。
-
-
List
-
ArrayList
ArrayList实现了List接口,是顺序容器,即元素存放的数据与放进去的顺序相同,允许放入null元素,底层通过数组实现。
当向容器中添加元素时,如果容量不足,容器会自动增大底层数组的大小。
为追求效率,ArrayList没有实现同步(synchronized),如果需要多个线程并发访问,用户可以手动同步,也可使用Vector替代。
-
Vector
Vector实现了List接口,可以用于存储和操作对象。Vector是线程安全的,多个线程可以同时对一个Vector进行操作,可以在多线程环境中使用而不需要额外的同步机制。
-
LinkedList
LinkedList同时实现了List接口和Deque接口,也就是说它既可以看作一个顺序容器,又可以看作一个队列(Queue),同时又可以看作一个栈(Stack)。底层通过双向链表实现。
为追求效率,LinkedList没有实现同步(synchronized),如果需要多个线程并发访问,可以先采用Collections.synchronizedList()方法对其进行包装。
-
-
Queue
Java里有一个叫做Stack的类,却没有叫做Queue的类(它是一个接口名字)。
-
ArrayDeque
Deque是double ended queue 表示双向的队列,由于Deque是双向的,所以可以对队列的头和尾都进行操作。
底层通过数组实现,为了满足可以同时在数组两端插入或删除元素的需求,该数组还必须是循环的,即循环数组。
ArrayDeque和LinkedList是Deque的两个通用实现,官方更推荐使用ArrayDeque用作栈和队列。ArrayDeque是非线程安全的。
-
LinkedList
-
PriorityQueue
PriorityQueue,即优先队列。优先队列的作用是能保证每次取出的元素都是队列中权值最小的。
元素大小的评判可以通过元素本身的自然顺序,也可以通过构造时传入的比较器。
-
-
- Map
-
TreeMap
Java TreeMap实现了SortedMap接口,也就是说会按照key的大小顺序对Map中的元素进行排序,key大小的评判可以通过其本身的自然顺序,也可以通过构造时传入的比较器。
TreeMap底层通过红黑树实现,也就意味着containsKey(), get(), put(), remove()都有着log(n)的时间复杂度。TreeMap是非同步的。
红黑树是一种近似平衡的二叉查找树,它能够明确保证任何一个节点的左右子树的高度差不会超过二者中较低那个的一倍。
红黑树是满足如下条件的二叉查找树:
1、每个节点要么是红色,要么是黑色。
2、根节点必须是黑色。
3、红色节点不能连续(也就是,红色节点的孩子和父亲都不能是红色。)
4、对于每个节点,从该点至null的任何路径,都含有相同个数的黑色节点。
-
HashMap
Java7 HashMap采用的是冲突链表方式。
将对象放入HashMap或HashSet中,需要注意hashCode()和equals()。hashCode()方法决定了对象会被放到哪个bucket里,当多个对象的哈希值冲突时,equals()方法决定了这些对象是否是同一个对象。
Java8 HashMap,由 数组 + 链表 + 红黑树 组成。在Java8中,当链表中的元素达到8个时,会将链表转换为红黑树,在这些位置进行查找的时候可以降低时间复杂度为O(logN)
-
HashTable
和HashMap类似,但它是线程安全的,这意味着同一时刻多个线程可以同时写入HashTable并且不会导致数据不一致。
它是遗留类,不应该使用它。现在可以使用ConcurrentHashMap来支持线程安全,并且ConcurrentHashMap的效率会更高,因为ConcurrentHashMap引入了分段锁。
-
LinkedHashMap
LinkedHashMap是linked list 和 HashMap的混合体,同时满足HashMap和linked list的某些特性。可将LinkedHashMap看作采用linked list增强的HashMap。
LinkedHashMap在HashMap的基础上,采用双向链表的形式将所有entry连接起来,保证元素的迭代顺序跟插入顺序相同。
出于性能原因,LinkedHashMap是非同步的,如果需要在多线程环境使用,需要程序员手动同步。
可以轻松实现一个采用FIFO替换策略 (先进先出) 的缓存。只需要在子类重载 protected boolean removeEldestEntry(Map.Entry<K,V> eldest) 方法,当元素个数超过一定数量时让removeEldestEntry() 返回true 就能实现一个固定大小的FIFO策略的缓存。
-
WeakHashMap
WeakHashMap里的entry可能会被GC自动删除,即使程序员没有调用remove()或者clear()方法。
WeakReference 弱引用,GC会在程序允许过程中自动判断哪些对象是可以被回收的,并在合适的时机进行内存释放。GC判断某个对象是否可被回收的依据是,是否有有效的引用指向该对象。
弱引用可以用来访问对象。但进行垃圾回收时弱引用并不会被考虑在内,仅有弱引用指向的对象仍然会被GC回收。
-