目录
1. ArrayList与LinkedList
ArrayList与LinkedList都实现了List接口。
(1)ArrayList
- 优点:便于对集合进行快速的随机访问。因为地址连续,一旦数据存储好了,查询操作效率比较高
- 缺点:插入和删除操作效率比较低 。
for (int i = size -1; i >= index ; i--) {
elementData[i +1] = elementData[i];//后移
}
(2)LinkedList
- 优点:插入和删除操作效率比较高
例如删除一个节点(前驱断开与当前节点的链接,连上当前节点的下一个节点),不用进行元素的搬移:
Node node = prev.next;
prev.next = node.next;
node.next = null;
- 缺点:查询操作效率比较低(只知道当前节点的地址,下一个节点的地址需要x.next)
Node x = head;
for (int i = 0; i < index; i++) {
x = x.next;
}
(3)二者的使用场景推荐
ArrayList使用场景:数组一开始就已经固定,后序很少进行插入或删除,多半是查询操作,尽量不对ArrayList进行插入或删除操作(删除尾部除外)
LinkedList使用场景:经常有删除/插入操作,而查询使用较少。
2. List与Set
List与Set都实现了collection接口。
(1)List
(2)Set
(3)二者的使用场景推荐
List:正常存储所有元素。Set:对集合中的元素进行去重。
3. TreeMap与HashMap
HashMap是无序的。
TreeMap是按键的升序排列的。
LinkedHashMap是按元素最后一次访问的时间从早到晚排序的。
(1)reeMap与HashMap比较
Map底层结构
| TreeMap | HashMap |
底层结构
|
红黑树
| 哈希桶 |
插入/删除/查找时间复杂度
| O(1) | |
是否有序
|
关于Key有序(大小关系由Comparable或比较器对象决定)
| 不一定有序 |
线程安全
|
不安全
|
不安全
|
插入/删除/查找区别
| 需要进行元素比较 |
1. 先计算key哈希地址 2. 然后进行查找,插入和删除
|
比较与覆写
|
key必须能够比较,否则会抛出ClassCastException异常
|
自定义类型需要覆写equals和hashCode方法
|
应用场景
| 需要Key有序场景下 |
Key是否有序不关心,需要更高的时间性能
|
key和value是否允许为空 | key不允许为空,value允许为空;key必须具备课比较的性质,或者传入比较器对象 | key和value都允许为空 |
HashMap通过hashcode对其内容进行快速查找,而 TreeMap中所有的元素都保持着某种固定的顺序,如果你需要得到一个有序的结果你就应该使用TreeMap(HashMap中元素的排列顺序是不固定的)。
HashMap:适用于在Map中插入、删除和定位元素。
Treemap:适用于按自然顺序或自定义顺序遍历键(key)。
4. TreeSet与HashSet
Set底层结构
| TreeSet | HashSet |
底层结构
|
红黑树
| 哈希桶 |
插入/删除/查找时间复杂度
| O(1) | |
是否有序
|
关于Key有序
| 不一定有序 |
线程安全
|
不安全
|
不安全
|
插入/删除/查找区别
| 按照红黑树的特性来进行查找,插入和删除 |
1. 先计算key哈希地址 2. 然后进行查找,插入和删除
|
比较与覆写
|
key必须能够比较,否则会抛出
ClassCastException异常
|
自定义类型需要覆写equals和
hashCode方法
|
应用场景
| 需要Key有序场景下 |
Key是否有序不关心,需要更高的时间性能
|
TreeSet集合对象的加入过程:
TreeSet的底层是通过二叉树来完成存储的,无序的集合
当我们将一个对象加入treeset中,treeset会将第一个对象作为根对象,然后调用对象的compareTo方法拿第二个对象和第一个比较,当返回至=0时,说明2个对象内容相等,treeset就不把第二个对象加入集合。返回>1时,说明第二个对象大于第一个对象,将第二个对象放在右边,返回-1时,则将第二个对象放在左边,依次类推。
HashSet集合对象的加入过程:
hashset底层是hash值的地址,它里面存的对象是无序的。
第一个对象进入集合时,hashset会调用object类的hashcode根据对象在堆内存里的地址调用对象重写的hashcode计算出一个hash值,然后第一个对象就进入hashset集合中的任意一个位置。
第二个对象开始进入集合,hashset先根据第二个对象在堆内存的地址调用对象的计算出一个hash值,如果第二个对象和第一个对象在堆内存里的地址是相同的,那么得到的hash值也是相同的,直接返回true,hash得到true后就不把第二个元素加入集合(这段是hash源码程序中的操作)。如果第二个对象和第一个对象在堆内存里地址是不同的,这时hashset类会先调用自己的方法遍历集合中的元素,当遍历到某个元素时,调用对象的equals方法,如果相等,返回true,则说明这两个对象的内容是相同的,hashset得到true后不会把第二个对象加入集合。
5. Set与Map
Map是一个接口类,该类没有继承自Collection,该类中存储的是<K,V>结构的键值对。
Set是一个接口类,该类继承自Collection,该类中存储的是Key。
Set 与 Map 的共同点:① key唯一,②Set底部采用Map实现