Java集合类是一种工具类,用于存储不定长度的数据。Java集合可以大致分为Set,List和Map三种体系,其中Set代表无序、不可重复的集合;List代表有序、重复的集合;而Map代表具有映射关系的集合。从Java 5之后又增加了Queue体系集合,代表一种队列集合实现。
集合类的出现是为了在编程时保存数量不确定的数据,以及具有映射关系的数据(也就是关系数组),所以也称集合类为容器类。集合类都位于Java.util包下,为解决线程并发问题Java 5之后还在Java.util.concurrent包下提供了支持多线程的集合类。其与数组不一样,数组元素可以保存基本数据类型的值,也可以是对象;而集合类只允许保存对象的引用变量。Java中的集合类主要有两个接口派生:Collection和Map,Collection和Map是Java集合框架的根接口,这两个接口又包含了一些子接口或实现类。
一:常用集合类之间的层次、继承关系
Collection|--List:元素是有序的,元素可以重复。因为飞机和体系有索引。
|--ArrayList:底层的数据结构使用的是数组结构。特点:查询速度快,但是增删稍慢。
|--LinkedList:底层使用的是链表数据结构。特点:增删速度很快,查询稍慢。
|--Vector:底层是数组结构,线程同步,被ArrayList替代了,因为效率低。
|--Set:元素是无序的(存入和取出的顺序不一定一致),元素不可以重复。
|--HashSet:底层数据结构是哈希表。HashSet通过hashCode和equals判断元素是否重复。如果元素的hashCode值相同,才会判断equals是否为true。如果元素的hashCode值不同,不会调用equals。对于判断元素是否存在,以及删除等操作依赖的方法是元素的hashCode和equals方法。
|--LinkedSet:通过hashcode确定元素的存储位置,同时通过链表确定元素的顺序。
|--TreeSet:可以对Set集合中的元素进行排序,底层数据结构是二叉树。它保证元素唯一性的依据是compareTo方法的return。TreeSet默认顺序采用的是红黑树。TreeSet允许自定义排序方式:当元素自身不具备比较性时,或者具备的比较性不是 所需的,这是就需要让集合自身具备比较性,在集合初始化时就让其具有比较性方式。
|--EnumSet:专门为枚举类设计的集合类,其中所有的元素都必须是指定枚举类型的枚举值,该枚举类型在创建EnumSet时显式或隐式的指定。EnumSet的集合元素也是有序的,EnumSet以枚举值在Enum内部的定义顺序来决定集合元素的顺序。
|--Map:用于保存具有映射关系的数据。
|--HashMap:底层数据结构是哈希表。HashMap通过hashCode和equals判断元素是否重复。如果元素的hashCode值相同,才会判断equals是否为true。如果元素的hashCode值不同,不会调用equals。
|--TreeMap:可以对Map集合中的元素进行排序,底层数据结构是二叉树。它保证元素唯一性的依据是compareTo方法的return。TreeSet默认顺序采用的是红黑树。TreeSet允许自定义排序方式:当元素自身不具备比较性时,或者具备的比较性不是 所需的,这是就需要让集合自身具备比较性,在集合初始化时就让其具有比较性方式。
|--EnumMap:与枚举类一起使用的Map实现,EnumMap中的所有KEY都必须是单个枚举类的枚举值。创建EnumMap的时候必须显式或隐式的指定它对应的枚举类。
|--Queue:用于模拟队列这种数据结构,不允许随机访问。
|--PriorityQueue:数据的存储不按照加入队列的顺序,而是按照队列元素的大小重新排序。因此,当取出队列元素时,取出的并不是最先加入队列元素而是最小的元素。
|--ArrayQueue:基于数组实现的是双端队列。
二:某些集合类的相互关系
Map集合的所有KEY将具有Set集合的特征,只要把Map的KEY集中起来,就是一个Set,这就实现了一个Map到Set的转换。其实,还可以实现从Set到Map的拓展。Set的底层是由Map实现的,可以说Set是Map的拓展。
我写了一个用Set实现Map,代码如下:
import java.util.HashSet;
import java.util.Iterator;
import java.util.Map;
import java.util.Map.Entry;
class SimpleEntry<K, V> implements Entry<K, V>, java.io.Serializable {
private final K key;
private V value;
public SimpleEntry(K key, V value) {
super();
this.key = key;
this.value = value;
}
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + ((key == null) ? 0 : key.hashCode());
return result;
}
@Override
public boolean equals(Object obj) {
if (obj == this) {
return true;
}
if (obj.getClass() == SimpleEntry.class) {
SimpleEntry se = (SimpleEntry) obj;
return se.getKey().equals(this.getKey());
}
return false;
}
@Override
public K getKey() {
// TODO Auto-generated method stub
return key;
}
@Override
public V getValue() {
// TODO Auto-generated method stub
return value;
}
@Override
public String toString() {
// TODO Auto-generated method stub
return super.toString();
}
@Override
public V setValue(V value) {
V oldValueV = this.value;
this.value = value;
return oldValueV;
}
}
public class Set2Map<K, V> extends HashSet<SimpleEntry<K, V>> {
public void clear() {
super.clear();
}
public boolean containskey(K key) {
return super.contains(new SimpleEntry<K, V>(key, null));
}
public boolean containsValue(Object value) {
for (SimpleEntry<K, V> se : this) {
if (se.getValue().equals(value)) {
return true;
}
}
return false;
}
public V get(Object key) {
for (SimpleEntry<K, V> se : this) {
if (se.getKey().equals(key)) {
return se.getValue();
}
}
return null;
}
public V put(K key, V value) {
add(new SimpleEntry<K, V>(key, value));
return value;
}
public void putAll(Map<? extends K, ? extends V> m) {
for (K key : m.keySet()) {
add(new SimpleEntry<K, V>(key, m.get(key)));
}
}
public V removeEntry(Object key) {
for (Iterator<SimpleEntry<K, V>> iterator = this.iterator(); iterator
.hasNext();) {
SimpleEntry<K, V> entry = (SimpleEntry<K, V>) iterator.next();
if (entry.getKey().equals(key)) {
V v = entry.getValue();
iterator.remove();
return v;
}
}
return null;
}
public int size() {
return super.size();
}
}
三、Java集合关系图