Java集合框架
Java 集合框架是提供了一套设计优良、易于使用和扩展的接口和类,用于存储和操作一组对象。集合框架位于java.util
包中,它提供了丰富的功能来处理数据集合,包括列表( List
)、集合( Set
)、队列( Queue
)、映射( Map
)等。
Collection
:这是集合层次结构中的根接口。它包含了用于添加、移除和搜索元素的方法。List
:继承自Collection
接口,是一个有序的集合,允许包含重复元素。支持通过索引来访问元素。- 实现类包括
ArrayList
、LinkedList
、Vector
等。
- 实现类包括
Set
:也是一个继承自Collection
接口的集合类型,但不允许包含重复元素。- 常见实现类有
HashSet
、LinkedHashSet
和TreeSet
。
- 常见实现类有
Queue
:通常用于实现 FIFO (先进先出)的数据结构,但也有其他变种如优先队列。- 优先级队列
PriorityQueue
是一个典型的实现。
- 优先级队列
Map
:不是Collection
接口的子接口,它存储键值对。Map
不能包含重复的键;每个键最多只能映射到一个值。- 常见实现类有
HashMap
、LinkedHashMap
和TreeMap
。
- 常见实现类有

Collection接口
Collection接口关系:

List接口实现类介绍
List
表示一个有序的、允许重复元素的集合,并且可以通过索引(位置)来访问和操作其中的元素。
常用方法:
add(E element)
:在列表末尾添加一个元素。add(int index, E element)
:在指定索引处插入一个元素。get(int index)
:返回指定索引处的元素。set(int index, E element)
:替换指定索引处的元素。remove(int index)
:删除指定索引处的元素。size()
:返回列表中的元素个数。indexOf(Object o)
:返回指定元素首次出现的索引,不存在则返回 -1。lastIndexOf(Object o)
:返回指定元素最后一次出现的索引。subList(int fromIndex, int toIndex)
:返回从 fromIndex 到 toIndex 的子列表。
List
接口的常见实现类:
ArrayList
:基于动态数组实现。更多阅读:ArrayList源码分析。LinkedList
:基于双向链表实现。更多阅读:LinkedList源码分析。ArrayList
与LinkedList
对比如下:
特性/类别 | ArrayList | LinkedList |
---|---|---|
数据结构 | 动态数组 | 双向链表 |
随机访问性能 | 快(O(1)) | 慢(O(n),需遍历查找) |
插入/删除头部 | 慢(O(n),需移动元素) | 快(O(1),只需修改头节点指针) |
插入/删除尾部 | 快(O(1),如果无需扩容) | 快(O(1),只需修改尾节点指针) |
插入/删除中间 | 慢(O(n),需移动元素) | 较快(O(n),但不涉及元素移动,仅修改指针) |
内存占用 | 因为是连续存储,所以内存使用较为紧凑 | 需要额外的空间存储指向前后的引用,内存开销较大 |
线程安全性 | 不是线程安全 | 不是线程安全 |
实现接口 | List , RandomAccess |
List , Deque |
适用场景 | 高效的随机访问,较少的插入和删除操作 | 高效的插入和删除操作,尤其是列表两端 |
Vector
(旧类,不建议使用 ):类似于ArrayList
,但它是一个同步(线程安全)的集合,它的所有的方法都被隐式地同步了(所有方法 synchronized ),这使得Vector
可以在多线程环境中安全使用。然而,由于同步带来的额外开销,使用这个类可能会导致性能下降。通常推荐在单线程环境下使用ArrayList
;在多线程并发场景下,使用Collections.synchronizedList(new ArrayList<>());
来创建一个线程安全的列表,或者直接使用并发集合如CopyOnWriteArrayList
。Stack
(旧类,不建议使用 ):扩展了Vector
,并实现了后进先出(LIFO, Last In First Out)的数据结构,也是一个同步(线程安全)的集合。它主要用于栈操作。与Vector
有同样的性能问题。官方文档推荐使用Deque
接口(双端队列)的实现类,如ArrayDeque
或LinkedList
代替。
Set接口实现类介绍
Set
集合不允许包含重复的元素(判断两个元素是否相同:根据元素的 equals()
方法判断);Set
不能像 List
一样可以通过整数索引来访问元素; Set
不保证元素的顺序,除非使用了特定类型的 Set
实现。
Set
接口常用方法:
Set
接口本身提供的方法不多,但因为它继承自 Collection
,所以它可以使用 Collection
接口中定义的所有方法,例如:
add(E e)
:如果Set
中尚未包含指定的元素,则将其添加到此集合中。remove(Object o)
:从此集合中移除指定元素(如果存在)。contains(Object o)
:如果此集合包含指定的元素,则返回true
。size()
:返回此集合中的元素数量。clear()
:移除此集合中的所有元素。iterator()
:返回在此集合中的元素上进行迭代的迭代器。
Set
接口的常见实现类:
HashSet
- 最常用的
Set
实现之一。 - 不保证元素的顺序,且允许
null
值。 - 通过哈希表 实现,提供了
O(1)
时间性能的基本操作(如添加、删除和查询)。
- 最常用的
LinkedHashSet
- 继承自
HashSet
,但是通过维护一个双向链表来记住元素插入的顺序。 - 提供了与
HashSet
相同的操作效率,并额外支持按插入顺序遍历集合。
- 继承自
TreeSet
- 基于红黑树的数据结构,能够对元素进行排序。
- 元素必须实现
Comparable
接口,或者在创建TreeSet
时提供一个Comparator
,以决定元素的排序方式。 - 支持自然排序或定制排序。
EnumSet
- 特别为枚举类型设计的高效实现:通过一个位向量( bit vector )来高效地存储和操作枚举类型的元素。
- 必须由同一个枚举类型的所有元素组成。
- 提供了非常快速的操作性能。
Queue接口实现类介绍
Queue
是专门用于表示队列的数据结构,队列通常遵循**先进先出( FIFO, First-In-First-Out )**原则,即最早加入队列的元素将首先被移除。不过,也有例外情况,比如优先级队列,它根据元素的优先级来决定服务顺序。
此外,Java还提供了 Deque
(双端队列)接口,允许从两端进行插入和删除操作,适用于栈、队列以及其他需要双向访问的数据结构。
Queue
接口常用方法:
add(E e)
/offer(E e)
:向队列尾部添加一个元素。add()
方法在插入失败时抛出异常,而offer()
返回一个布尔值。remove()
/poll()
:从队列头部移除并返回一个元素。remove()
在队列为空时抛出异常,而poll()
则返回null
。element()
/peek()
:获取但不移除队列头部的元素。element()
方法在队列为空时抛出异常,而peek()
返回null
。
Queue
接口的常见实现类:
LinkedList
:实现了Queue
接口,并且可以作为双端队列使用。它允许在两端进行高效的插入和删除操作。PriorityQueue
:基于堆 的数据结构,按照元素的自然顺序或通过提供的Comparator
来进行排序。因此,它并不严格遵守FIFO原则,而是根据优先级来确定哪个元素最先出队。
Map接口
Map
接口是集合框架的一部分,但它并不继承自 Collection
接口。 Map
用于存储键值对( key-value pairs ),其中每个键都是唯一的,而值可以重复。通过键可以在 Map
中高效地查找、更新或删除对应的值。
Map
接口和类关系:

Map
接口常用方法:
- 基本操作:
put(K key, V value)
:将指定的键值对插入到Map
中。get(Object key)
:根据键返回对应的值。remove(Object key)
:根据键移除键值对。clear()
:移除Map
中的所有映射关系。isEmpty()
:检查Map
是否为空。size()
:返回Map
中键值对的数量。
- 查询操作:
containsKey(Object key)
:判断Map
是否包含指定的键。containsValue(Object value)
:判断Map
是否包含指定的值。keySet()
:返回Map
中所有键的集合视图。values()
:返回Map
中所有值的集合视图。entrySet()
:返回Map
中所有键值对的集合视图。
Map
接口的常见实现类:
HashMap
- 最常用的实现之一,基于哈希表实现。
- 允许
null
键和null
值。 - 不保证顺序。
LinkedHashMap
- 继承自
HashMap
,但通过维护双向链表来记住元素的插入顺序。 - 可以基于访问顺序进行排序(适合实现LRU缓存)。
- 继承自
TreeMap
- 基于红黑树 数据结构,按键的自然顺序或自定义的
Comparator
进行排序。 - 不允许
null
键。
- 基于红黑树 数据结构,按键的自然顺序或自定义的
Hashtable
(旧类,不推荐使用)- 类似于
HashMap
,但是是同步的(线程安全),性能较差。 - 不允许
null
键和null
值。 - 替代类:
ConcurrentHashMap
,专门设计用于高并发环境的线程安全HashMap实现,通过分段锁(在 Java 8 前)或数组 + 链表/红黑树(在 Java 8 及以后使用 synchronized 和 CAS )实现高效的并发访问,允许多个线程同时读写而不会导致数据竞争,从而提供高并发场景下的线程安全和性能优化。
- 类似于
EnumMap
- 专门用于键为枚举类型的情况(要求所有键必须来自同一个枚举类型),针对枚举类型的键进行了特别优化,提供了更高效的存储和访问速度。