文章目录

  • 前言
  • 一、LinKedHashMap源码分析:
    • 继承关系:
    • 属性:
    • 构造器:
    • 私有内部类
    • put 方法:
    • LinKedHashMap总结
  • 二、TreeMap源码分析:
    • 继承关系:
    • 属性:
    • 构造器:
    • 私有内部类
    • 方法:
    • TreeMap总结:

前言

我们对LinKedHashMap和TreeMap研究都是基于HashMap为参考来研究一下他们独有的特点,和维护这些特点的方法。


提示:以下是本篇文章正文内容,下面案例可供参考

一、LinKedHashMap源码分析:

LinKedHashMap继承自HashMap<K,V> 具有HashMap的所有特性:Key不能重复、Key value都可以为null 线程不安全
相比HashMap来说LinkedHashMap具有有序性(插入有序)

继承关系:

public class LinkedHashMap<K,V>extends HashMap<K,V>implements Map<K,V>

可以看出LinkedHashMap是基于HashMap实现的

属性:

默认值、扩容机制都和HashMap的特征一样
特有的属性:

transient LinkedHashMap.Entry<K,V> head;//头结点
transient LinkedHashMap.Entry<K,V> tail;//尾结点

构造器:

构造器调用HashMap的构造器
新增一个构造器:
boolean型的accessOrder 用来判断顺序性
true 访问有序 false 插入有序 默认值:false

public LinkedHashMap(int initialCapacity,float loadFactor,boolean accessOrder) {super(initialCapacity, loadFactor);this.accessOrder = accessOrder;}

私有内部类

Entry<K,V>内部类继承与HashMap的内部类Node 增加了 head tail 用来保证有序性。
注释:插入有序即 按照插入时的顺序保持有序 访问有序即访问后将此数据移动到末尾。

static class Entry<K,V> extends HashMap.Node<K,V> {Entry<K,V> before, after; //前缀和后缀Entry(int hash, K key, V value, Node<K,V> next) {super(hash, key, value, next);}}

put 方法:

直接使用put方法调用的是父类的put方法但在put方法里面调用的newNode方法是子类重写的


public V put(K key, V value) {return putVal(hash(key), key, value, false, true);}
inal V putVal(int hash, K key, V value, boolean onlyIfAbsent,boolean evict) {Node<K,V>[] tab; Node<K,V> p; int n, i;//判断数组是否为空,为空则对tab进行扩容扩容后将新数组的长度赋值给n。if ((tab = table) == null || (n = tab.length) == 0)n = (tab = resize()).length;//判断此hash对应的数组位置是否为Null 如果为null 用子类newNode方法赋值if ((p = tab[i = (n - 1) & hash]) == null)tab[i] = newNode(hash, key, value, null);else {Node<K,V> e; K k;//先判断链表首位的hash和此新传入的hash是否相等在判断k值是否相等,相等的话将首尾p赋值给eif (p.hash == hash &&((k = p.key) == key || (key != null && key.equals(k))))e = p;//判断p是否在红黑树上else if (p instanceof TreeNode)e = ((TreeNode<K,V>)p).putTreeVal(this, tab, hash, key, value);else {//不在红黑树也不在首位的话遍历链表for (int binCount = 0; ; ++binCount) {//如果遍历到末尾给末尾赋值新创建的newNide;if ((e = p.next) == null) {p.next = newNode(hash, key, value, null);//如果遍历到链表长度之外的话if (binCount >= TREEIFY_THRESHOLD - 1) // -1 for 1sttreeifyBin(tab, hash);break;}//如果hash值与链表中以为hash值相等或者K值相等的话退出循环if (e.hash == hash &&((k = e.key) == key || (key != null && key.equals(k))))break;//更新pp = e;}}if (e != null) { // existing mapping for keyV oldValue = e.value;if (!onlyIfAbsent || oldValue == null)e.value = value;afterNodeAccess(e);return oldValue;}}++modCount;if (++size > threshold)resize();afterNodeInsertion(evict);return null;}//子类:Node<K,V> newNode(int hash, K key, V value, Node<K,V> e) {新建一个Entry 赋值给 P      LinkedHashMap.Entry<K,V> p =new LinkedHashMap.Entry<>(hash, key, value, e);使用linkNodeLast方法对p进行重新操作(更新头结点,尾结点和前缀后缀等属性)linkNodeLast(p);return p;}
private void linkNodeLast(LinkedHashMap.Entry<K,V> p) {LinkedHashMap.Entry<K,V> last = tail;tail = p;//如果尾结点为null说明此链表之前没有Entry<K,V>将p赋值给头结点head// 否则更新p的前缀为之前的尾结点原来尾结点的后缀更新为Pif (last == null)head = p;else {p.before = last;last.after = p;}}

LinKedHashMap总结

从上面我们可以看出LinKedHashMap相比于HashMap保证的数据的有序性,他的有序性保证是在HashMap原有的基础上给每个数据添加了双向链表来达到数据的有序性

二、TreeMap源码分析:

TreeMap保证map的key可以大小排序,key不能为null (NullPointerException)value可以为null,key不能重复

继承关系:

继承AbstractMap所有方法
实现了 NavigableMap和Serializable(可序列化)接口

public class TreeMap<K,V>extends AbstractMap<K,V>implements NavigableMap<K,V>, Cloneable, java.io.Serializable

我们来介绍一下 NavigableMap主要作用就不分析源码了

1. NavigableMap 继承自 SortedMap,所以它的元素是有序的。
2. 在 SortedMap 基础上,支持快速搜索符合条件的最近的元素。这里条件主要是指     lower(>), floor(>=), ceiling(<),higher(>)。
3. 支持逆序访问。 descendingKeySet / descendingMap。
4. 支持获取子集合,集合边界元素是否包含是可配的 subMap headMap  tailMap 。

通过上述我们就可以知道TreeMap同样也具备如上的功能

属性:

public Comparator<? super K> comparator() { //比较器return comparator;}private transient Entry<K,V> root = null; //root属性,红黑树的根节点,是entry类型entry节点根据key进行排序

构造器:

相比于HashMap来说提供了比较器用来对数据进行排序

//空参构造器使用默认比较器
public TreeMap() {comparator = null;}
//实现comparator的构造器public TreeMap(Comparator<? super K> comparator) {this.comparator = comparator;}//传入数据的构造器   public TreeMap(Map<? extends K, ? extends V> m) {comparator = null;putAll(m);}//带有comparator方法的类 public TreeMap(SortedMap<K, ? extends V> m) {comparator = m.comparator();try {buildFromSorted(m.size(), m.entrySet().iterator(), null, null);} catch (java.io.IOException | ClassNotFoundException cannotHappen) {}}

私有内部类

相比较HashMap来说内部类Entry增加了左右孩子父节点还有颜色的属性来实现红黑树储存数据

static final class Entry<K,V> implements Map.Entry<K,V> {K key;  //键V value; //值Entry<K,V> left;   //左孩子Entry<K,V> right;    //右孩子Entry<K,V> parent;   //父节点boolean color = BLACK;    //颜色 默认黑色Entry(K key, V value, Entry<K,V> parent) {this.key = key;this.value = value;this.parent = parent;}

方法:

因为TreeMap继承自NavigableMap的所以也具有他的一些方法:
lower(>), floor(>=), ceiling(<),higher(>) //快速查找
descendingKeySet / descendingMap //逆序访问
subMap headMap tailMap //获取子集合

TreeMap总结:

TreeMap底层是基于红黑树实现了,所以他支持快速查询方法 并且它的构造器可传入了比较器可以自定义数据的排序方法

LinKedHashMap和TreeMap介绍相关推荐

  1. Java—Map集合详解(HashMap/Hashtable/LinkedHashMap/Properties/TreeMap/WeakHashMap/IdentityHashMap/EnumMap)

    关注微信公众号:CodingTechWork,一起学习进步. Map Map集合介绍   Map(也称为字典.关联数组)是用于保存具有映射关系的数据,保存两组值,key和value,这两组值可以是任何 ...

  2. Java(ArrayList和LinkedList)、(HashTable与HashMap)、(HashMap、Hashtable、LinkedHashMap和TreeMap比较)

    1.ArrayList和LinkedList (1)ArrayList是实现了基于动态数组的数据结构,LinkedList基于链表的数据结构.  (2)对于随机访问get和set,ArrayList绝 ...

  3. HashMap, LinkedHashMap 和 TreeMap的区别

    HashMap, LinkedHashMap 和 TreeMap的区别 Java里面的HashMap, LinkedHashMap 和 TreeMap 有什么区别?我看不出以下3个key和value有 ...

  4. HashMap、LinkedHashMap、TreeMap的深入认识

    HashMap,LinkedHashMap,TreeMap都属于Map. Map 主要用于存储键(key)值(value)对,根据键得到值,因此键不允许键重复,但允许值重复. HashMap 是一个最 ...

  5. 有序Map集合:LinkedHashMap和TreeMap该如何选用

    文章目录 前言 一.为什么HashMap是无序的 二.LinkedHashMap如何保证有序性 三.TreeMap的底层原理 四.LinkedHashMap和TreeMap比较 总结 前言 为什么Ha ...

  6. java treemap 内存_Java中Map、HashMap、LinkedHashMap、TreeMap的区别

    Map: Map是一个接口不能实例化,Map接口主要有两个实现类:HashMap和TreeMap类.其中,HashMap类按哈希算法来存取对象,而TreeMap类可以对键对象进行排序: Map提供了一 ...

  7. Java中HashMap、LinkedHashMap和TreeMap区别使用场景

    1. HashMap中k的值没有顺序,常用来做统计. 2.LinkedHashMap吧.它内部有一个链表,保持Key插入的顺序.迭代的时候,也是按照插入顺序迭代,而且迭代比HashMap快. 3. T ...

  8. Java之HashMap、Hashtable、LinkedHashMap、TreeMap、ConcurrentHashMap简单的区别

    一. HashMap 1)底层实现  数组+链表+红黑树(在JDK1.8中如果链表长度大于8的时候才转换为红黑树) 2)是否线程安全 不支持线程的同步,线程不安全,如需同步,可用Collections ...

  9. LinkedHashMap和TreeMap的有序性

    做一个数组的多属性动态排序的功能,使用map时发现有序性问题. LinkedHashMap会存储数据的插入顺序,是进入时有序:TreeMap则是默认key升序,是进入后有序(hashMap .hash ...

最新文章

  1. mysql数据库报错1146_关于MySQL报错:[ERR] 1146
  2. 让容器跑得更快:CPU Burst 技术实践
  3. GenericUDF使用流程记载(转载+自己整理)
  4. java多线程流式写入文件夹_java多线程写入同一文件
  5. java中白盒测试用例_基于JAVA开发的中国象棋游戏的开发与研究白盒测试用例.doc...
  6. 面试精讲之面试考点及大厂真题 - 分布式专栏 09 缓存必问:Reids持久化,高可用集群
  7. 2017.7.26 奇怪的道路 失败总结
  8. fastdfs删除过期文件_Spring Boot 系列:使用 Spring Boot 集成 FastDFS
  9. apipost提示error:invalid protocol的解决方案
  10. android中搭建NDK环境及使用JNI技术
  11. 如何调整金格电子章服务器印章_电子签章赋能勘察设计新动力
  12. 用c#转换word或excel文档为html文件,C#实现DataSet内数据转化为Excel和Word文件的通用类完整实例...
  13. garmone build on sb2
  14. Synergy——使用一套键鼠控制两台电脑(Ubuntu 和 Windows)
  15. java单循环赛制程序_单循环比赛的固定轮转编排法与贝格尔编排法
  16. 计算机桌面图标损坏,win7系统的电脑桌面图标受到损坏要如何修复
  17. 前端vue地图自动定位当前位置
  18. 计算机动画原理课程设计选题,组成原理课程设计设计一台模型计算机.pdf
  19. 深析Vue双向数据绑定(MVVM模型)
  20. 娱乐之神兽羊驼(原创)

热门文章

  1. Delphi绘制Alpha图像的函数
  2. Python-数学篇之计算方法的目录:
  3. 基于傅里叶变换的音频重采样算法 (附完整c代码)
  4. android -------- NDK 入门指南
  5. SpringMvc自动代理
  6. 自由缩放属性resize
  7. 信息系统项目管理师培训感言
  8. lua userdata
  9. Python学习笔记四(Python OS模块)
  10. 删除数据库日志sql语句