美文网首页
Java中的HashMap之get

Java中的HashMap之get

作者: 被虐的小鸡 | 来源:发表于2020-04-04 11:24 被阅读0次

如有转载请注明出处 https://www.jianshu.com/p/f4b5a7025f86

粗略说一说

HashMap主要是由数组+链表数据结构实现的,数组存储链表,而链表中存储了上一个节点地址、下一个节点地址、key和value的值,在jdk1.8中加入了红黑树,当链表的长度超过一定阈值的时候会转换成红黑树。


接下来我们就详细挖一下每一部分都做了什么。

get(Object key)

当我们要获取hashMap中的value时,需要根据key来调用get方法,那我们看一看get方法做了什么操作。

  public V get(Object key) {
        Node<K,V> e;
        return (e = getNode(hash(key), key)) == null ? null : e.value;
    }

在return中我们可以看到通过getNode方法获取链表中的某一个node节点,如果node不为空则返回node中的value,如果node为null则返回null。
在getNode方法中第一个参数是对key的hashCode进行了hash处理,hash是通过散列算法将一些长度不一样的数据转换成长度一样的数据。一般通过加法,位运算,乘法来获取hash。

举个例子:
aa  -> aadb
bbb -> bbbc
c   -> cedc
那我们来看看hash(key)是如何生成的?
static final int hash(Object key) {
        int h;
        return (key == null) ? 0 : (h = key.hashCode()) ^ (h >>> 16);
 }
Object的hashCode()通过将物理地址进行hash,然后将hash值右移16位让高位的参加运算再进行按照位的异或来生成的,这样能保证生成的数据更加散列。
final Node<K,V> getNode(int hash, Object key) {
        Node<K,V>[] tab; Node<K,V> first, e; int n; K k;
        if ((tab = table) != null && (n = tab.length) > 0 &&
            (first = tab[(n - 1) & hash]) != null) {
            if (first.hash == hash && // always check first node
                ((k = first.key) == key || (key != null && key.equals(k))))
                return first;
            if ((e = first.next) != null) {
                if (first instanceof TreeNode)
                    return ((TreeNode<K,V>)first).getTreeNode(hash, key);
                do {
                    if (e.hash == hash &&
                        ((k = e.key) == key || (key != null && key.equals(k))))
                        return e;
                } while ((e = e.next) != null);
            }
        }
        return null;
    }

(n - 1) & hash 可以得到hash值在数组中的下标,按位与得到的是0-n-1范围内的值

假设key得到的hash值为2135657,他的二进制是
0000 0000 0010 0000 1001 0110 0110 1001
当前数组的长度是9,那么n-1为8,他的二进制是
0000 0000 0000 0000 0000 0000 0000 1000
进行&运算之后得到的就是8,当前的key对应的hash值就在数组中的8位置

之后的操作就比较简单了,先判断链表中的第一个节点的key是否相同,如果是对象就判断地址是否相同,如果地址不相同在判断里面存的值是否相同,如果链表的第一个节点不匹配,那么就判断是否是红黑二叉树,如果是的话就在树中进行查找,如果不是树结构就接着找链表后面的节点。

相关文章

  • Java中的HashMap之get

    如有转载请注明出处 https://www.jianshu.com/p/f4b5a7025f86 粗略说一说 Ha...

  • Java基础之HashMap的原理

    Java中的HashMap是怎么工作的?本文将通过自己定义HashMap的 put,get,remove的方法来简...

  • Java HashMap

    面试的时候经常会遇见诸如:“java中的HashMap是怎么工作的”,“HashMap的get和put内部的工作原...

  • HashMap原理

    面试的时候经常会遇见诸如:“java中的HashMap是怎么工作的”,“HashMap的get和put内部的工作原...

  • java源码分析之LinkedHashMap

    相关文章java源码分析之HashMap(一)java源码分析之HashMap(二)java源码分析之HashMa...

  • java源码分析之HashMap(三)

    相关文章java源码分析之HashMap(一)java源码分析之HashMap(二)https://blog.cs...

  • HashMap的get效率初探

    HashMap是java中用的非常多的一个容器,HashMap实现了Map接口的V get(K key)...

  • Java8 HashMap源码解析

    前言 Java7中的HashMap和Java8中的HashMap不太一样,Java7中的HashMap主要是由数组...

  • Java中的集合框架学习之HashMap 详解

    Java中的集合框架学习之HashMap 详解 以下是HashMap的基本用法: 方法一: 1.通过keySet得...

  • java基础之集合略解

    Java集合:整体结构 HashMap剖析 Java 集合系列10之 HashMap详细介绍(源码解析)和使用示例...

网友评论

      本文标题:Java中的HashMap之get

      本文链接:https://www.haomeiwen.com/subject/jcnkphtx.html