总觉得很久没有总结一些基础知识了。很空虚,所以想着那就总结一下java中的集合类吧。
常用的集合类有ArrayList,LinkList,Vector,HashMap,HashTable,HashSet这几种。主要通过对比这些集合之间的区别和内部机制来总结一下各自的特点。
1、ArrayList和LinkList和Vector
三者的共同点是都实现了List接口
不同点:
1、内部实现
ArrayList和Vector内部是数组实现的,而LinkList则是双向链表。
数组的实现方式
2、初始化
ArrayList在初始化时是一个空的数组,只要在具体执行的时候才会去初始化数组默认是10,。
可以根据传入参数进行初始化。
Vector是在构造方法时就初始化一个大小为10的数组。可以根据初始化参数来修改大小。
3、扩容
ArrayList当数组大小不能满足新增元素的时候,会进行扩容,每次扩容为原来大小的1.5倍 (old+old>>1)
Vector 在初始化时可以通过构造函数初始化初始容量和增量因子。默认增量因子为0,如果为0,则扩容为原来的2倍,如果大于0,则为原始容量+增量
4、安全机制。
ArrayList和LinkList都是线程不安全的。vector线程安全。add、remove、get(int)通过synchronized加锁。
Collections.synchronizedList() 可以保证线程安全,但是效率太低。
此外线程安全的list还有
copyOnWriteArrayList(写时复制),只有在写方法添加了ReentrantLock锁。读方法没有加锁,这样可以提高效率。适用于读大于写的情景。
2、HashMap,Hashtable,HashSet
这三者相同点是底层都是以key-value为基础。
HashSet底层都是实例化了一个HashMap,只是value为null;
HashMap和HashTable都是Entry对象。底层都是数组和链表(tree)的数据结构。
不同点:
1、实现的接口
HashMap和Hashtable实现了Map接口。HashSet实现了Set接口。
2、是否可以为null。
hashMap和HashSet都允许为null,而hashtable不允许key和value为null。
这个可能是当时设计思路的原因,所以在Hashtable中对此作了处理,如果value为null会直接抛出空指针异常,如果key为null则在计算hashcode时也会空指针异常。
3、安全性。
HashTable是线程安全的,通过synchronized加锁
HashMap和HashSet是线程不安全的。
线程安全的map有concurrentHashMap,通过分段加lock锁实现。
以上是我总结的一些集合中的特点比较基础,之后会继续补充。