线性表数据结构解读(五)哈希表结构-HashMap

来源:互联网 发布:淘宝一阳指是什么 编辑:程序博客网 时间:2024/06/14 18:41

   前面的博客中,我给大家分析过数组和链表两种线性表数据结构。数组存储区间连续,查找方便,但是插入和删除效率低下;链表存储区间离散,插入删除方便,但是查找困难。大家肯定会问,有没有一种结构,既能做到查找便捷,又能做到插入删除方便呢?答案就是我们今天要跟大家说的主角:哈希表。 
    我们先来看一下哈希表的百度定义

散列表(Hash table,也叫哈希表),是根据关键码值(Keyvalue)而直接进行访问的数据结构。也就是说,它通过把关键码值映射到表中一个位置来访问记录,以加快查找的速度。这个映射函数叫做散列函数,存放记录的数组叫做散列表。 
给定表M,存在函数f(key),对任意给定的关键字值key,代入函数后若能得到包含该关键字的记录在表中的地址,则称表M为哈希(Hash)表,函数f(key)为哈希(Hash)函数。

下图是一个经典的哈希表实现方式图,来自百度百科。

这里写图片描述

再看一张图

这里写图片描述

    这张图更明显的告诉我们哈希表采用的是一种“拉链法”实现的,关于拉链法,大家可以自行百度脑补。左边是数组,右边是链表,感觉十分像用数组把链表串起来,在一个长度为16的数组中,每个元素存储的是一个链表的头结点。接下来我们一起来分析一下HashMap的源码实现。

HashMap的继承关系

这里写图片描述

通过HashMap的继承关系,我们可以得知HashMap继承自抽象类AbstractMap,该Map又实现了Map接口,我们下来看一下Map接口包含哪些方法。

这里写图片描述

可以看出包含了我们常用的HashMap中的一些方法,接着我们来看HashMap的父类AbstractMap。

<code class="hljs php has-numbering" style="display: block; padding: 0px; color: inherit; box-sizing: border-box; font-family: "Source Code Pro", monospace;font-size:undefined; white-space: pre; border-radius: 0px; word-wrap: normal; background: transparent;"><span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">abstract</span> <span class="hljs-class" style="box-sizing: border-box;"><span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">class</span> <span class="hljs-title" style="box-sizing: border-box; color: rgb(102, 0, 102);">AbstractMap</span><<span class="hljs-title" style="box-sizing: border-box; color: rgb(102, 0, 102);">K</span>, <span class="hljs-title" style="box-sizing: border-box; color: rgb(102, 0, 102);">V</span>> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">implements</span> <span class="hljs-title" style="box-sizing: border-box; color: rgb(102, 0, 102);">Map</span><<span class="hljs-title" style="box-sizing: border-box; color: rgb(102, 0, 102);">K</span>, <span class="hljs-title" style="box-sizing: border-box; color: rgb(102, 0, 102);">V</span>> {</span>    <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 用懒加载的方式定义了Set集合类型的键,表明HashMap键是不能重复的</span>    Set<K> keySet;    <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 用懒加载的方式定义了Collection集合类型的值,表明HashMap值是可以重复的</span>    Collection<V> valuesCollection;    ……}</code><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li></ul><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li></ul>

这里重点要看明白一开始定义的键和值,键是不能重复的,值可以重复。 
然后定义了两个静态的实体类

<code class="hljs fsharp has-numbering" style="display: block; padding: 0px; color: inherit; box-sizing: border-box; font-family: "Source Code Pro", monospace;font-size:undefined; white-space: pre; border-radius: 0px; word-wrap: normal; background: transparent;"><span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 维护键和值的 Entry</span><span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">static</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">class</span> AbstractMap.SimpleEntry<K,V>  <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 维护不可变的键和值的 Entry</span><span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">static</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">class</span> AbstractMap.SimpleImmutableEntry<K,V>           </code><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li></ul><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li></ul>

继续下面实现了接口Map中的方法:clear、put、get、equals、size、hashCode等等。

HashMap源码解析

现在我们开始分析HashMap的源码,走起┏ (゜ω゜)=☞

元素定义

<code class="hljs java has-numbering" style="display: block; padding: 0px; color: inherit; box-sizing: border-box; font-family: "Source Code Pro", monospace;font-size:undefined; white-space: pre; border-radius: 0px; word-wrap: normal; background: transparent;">    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">private</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">static</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">final</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> MINIMUM_CAPACITY = <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">4</span>;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// HashMap最小容量为4</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">private</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">static</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">final</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> MAXIMUM_CAPACITY = <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">1</span> << <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">30</span>;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// HashMap最大容量1073741824,往右移除2,往左移是乘2</span>    <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 实体数组</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">private</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">static</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">final</span> Entry[] EMPTY_TABLE            = <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">new</span> HashMapEntry[MINIMUM_CAPACITY >>> <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">1</span>];<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 一个空的键值对实体数组最小容量是2</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">static</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">final</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">float</span> DEFAULT_LOAD_FACTOR = <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">.75</span>F;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 默认的容量扩展因子是0.75</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">transient</span> HashMapEntry<K, V>[] table;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 键值对的数组</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">transient</span> HashMapEntry<K, V> entryForNullKey;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 没有键的键值对</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">transient</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> size;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 非空元素长度</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">transient</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> modCount;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 计数器</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">private</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">transient</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> threshold;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 容量因子的极限</span>    <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// Views - lazily initialized 父类继承下来的</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">private</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">transient</span> Set<K> keySet;    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">private</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">transient</span> Set<Entry<K, V>> entrySet;    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">private</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">transient</span> Collection<V> values;</code><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li><li style="box-sizing: border-box; padding: 0px 5px;">9</li><li style="box-sizing: border-box; padding: 0px 5px;">10</li><li style="box-sizing: border-box; padding: 0px 5px;">11</li><li style="box-sizing: border-box; padding: 0px 5px;">12</li><li style="box-sizing: border-box; padding: 0px 5px;">13</li><li style="box-sizing: border-box; padding: 0px 5px;">14</li><li style="box-sizing: border-box; padding: 0px 5px;">15</li><li style="box-sizing: border-box; padding: 0px 5px;">16</li><li style="box-sizing: border-box; padding: 0px 5px;">17</li><li style="box-sizing: border-box; padding: 0px 5px;">18</li><li style="box-sizing: border-box; padding: 0px 5px;">19</li><li style="box-sizing: border-box; padding: 0px 5px;">20</li><li style="box-sizing: border-box; padding: 0px 5px;">21</li><li style="box-sizing: border-box; padding: 0px 5px;">22</li><li style="box-sizing: border-box; padding: 0px 5px;">23</li><li style="box-sizing: border-box; padding: 0px 5px;">24</li></ul><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li><li style="box-sizing: border-box; padding: 0px 5px;">9</li><li style="box-sizing: border-box; padding: 0px 5px;">10</li><li style="box-sizing: border-box; padding: 0px 5px;">11</li><li style="box-sizing: border-box; padding: 0px 5px;">12</li><li style="box-sizing: border-box; padding: 0px 5px;">13</li><li style="box-sizing: border-box; padding: 0px 5px;">14</li><li style="box-sizing: border-box; padding: 0px 5px;">15</li><li style="box-sizing: border-box; padding: 0px 5px;">16</li><li style="box-sizing: border-box; padding: 0px 5px;">17</li><li style="box-sizing: border-box; padding: 0px 5px;">18</li><li style="box-sizing: border-box; padding: 0px 5px;">19</li><li style="box-sizing: border-box; padding: 0px 5px;">20</li><li style="box-sizing: border-box; padding: 0px 5px;">21</li><li style="box-sizing: border-box; padding: 0px 5px;">22</li><li style="box-sizing: border-box; padding: 0px 5px;">23</li><li style="box-sizing: border-box; padding: 0px 5px;">24</li></ul>

构造方法

<code class="hljs java has-numbering" style="display: block; padding: 0px; color: inherit; box-sizing: border-box; font-family: "Source Code Pro", monospace;font-size:undefined; white-space: pre; border-radius: 0px; word-wrap: normal; background: transparent;">    <span class="hljs-javadoc" style="color: rgb(136, 0, 0); box-sizing: border-box;">/**     * Constructs a new empty {@code HashMap} instance.     */</span>    <span class="hljs-annotation" style="color: rgb(155, 133, 157); box-sizing: border-box;">@SuppressWarnings</span>(<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"unchecked"</span>)    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-title" style="box-sizing: border-box;">HashMap</span>() {        table = (HashMapEntry<K, V>[]) EMPTY_TABLE;        threshold = -<span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">1</span>; <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// Forces first put invocation to replace EMPTY_TABLE</span>    }    <span class="hljs-javadoc" style="color: rgb(136, 0, 0); box-sizing: border-box;">/**     * 指定初始容量的构造方法     */</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-title" style="box-sizing: border-box;">HashMap</span>(<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> capacity) {        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (capacity < <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">0</span>) {            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">throw</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">new</span> IllegalArgumentException(<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"Capacity: "</span> + capacity);        }        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (capacity == <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">0</span>) {            <span class="hljs-annotation" style="color: rgb(155, 133, 157); box-sizing: border-box;">@SuppressWarnings</span>(<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"unchecked"</span>)            HashMapEntry<K, V>[] tab = (HashMapEntry<K, V>[]) EMPTY_TABLE;            table = tab;            threshold = -<span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">1</span>; <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// Forces first put() to replace EMPTY_TABLE</span>            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">return</span>;        }        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (capacity < MINIMUM_CAPACITY) {            capacity = MINIMUM_CAPACITY;        } <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">else</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (capacity > MAXIMUM_CAPACITY) {            capacity = MAXIMUM_CAPACITY;        } <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">else</span> {            capacity = Collections.roundUpToPowerOfTwo(capacity);        }        makeTable(capacity);    }    <span class="hljs-javadoc" style="color: rgb(136, 0, 0); box-sizing: border-box;">/**     * 指定初始容量和扩展因子的构造方法     */</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-title" style="box-sizing: border-box;">HashMap</span>(<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> capacity, <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">float</span> loadFactor) {        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">this</span>(capacity);        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (loadFactor <= <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">0</span> || Float.isNaN(loadFactor)) {            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">throw</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">new</span> IllegalArgumentException(<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"Load factor: "</span> + loadFactor);        }        <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">/*         * Note that this implementation ignores loadFactor; it always uses         * a load factor of 3/4. This simplifies the code and generally         * improves performance.         */</span>    }    <span class="hljs-javadoc" style="color: rgb(136, 0, 0); box-sizing: border-box;">/**     * 构造一个映射关系与指定 Map 相同的新 HashMap。所创建的 HashMap 具有默认加载因子 (0.75) 和足  以容纳指定 Map 中映射关系的初始容量。      */</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-title" style="box-sizing: border-box;">HashMap</span>(Map<? extends K, ? extends V> map) {        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">this</span>(capacityForInitSize(map.size()));        constructorPutAll(map);    }</code><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li><li style="box-sizing: border-box; padding: 0px 5px;">9</li><li style="box-sizing: border-box; padding: 0px 5px;">10</li><li style="box-sizing: border-box; padding: 0px 5px;">11</li><li style="box-sizing: border-box; padding: 0px 5px;">12</li><li style="box-sizing: border-box; padding: 0px 5px;">13</li><li style="box-sizing: border-box; padding: 0px 5px;">14</li><li style="box-sizing: border-box; padding: 0px 5px;">15</li><li style="box-sizing: border-box; padding: 0px 5px;">16</li><li style="box-sizing: border-box; padding: 0px 5px;">17</li><li style="box-sizing: border-box; padding: 0px 5px;">18</li><li style="box-sizing: border-box; padding: 0px 5px;">19</li><li style="box-sizing: border-box; padding: 0px 5px;">20</li><li style="box-sizing: border-box; padding: 0px 5px;">21</li><li style="box-sizing: border-box; padding: 0px 5px;">22</li><li style="box-sizing: border-box; padding: 0px 5px;">23</li><li style="box-sizing: border-box; padding: 0px 5px;">24</li><li style="box-sizing: border-box; padding: 0px 5px;">25</li><li style="box-sizing: border-box; padding: 0px 5px;">26</li><li style="box-sizing: border-box; padding: 0px 5px;">27</li><li style="box-sizing: border-box; padding: 0px 5px;">28</li><li style="box-sizing: border-box; padding: 0px 5px;">29</li><li style="box-sizing: border-box; padding: 0px 5px;">30</li><li style="box-sizing: border-box; padding: 0px 5px;">31</li><li style="box-sizing: border-box; padding: 0px 5px;">32</li><li style="box-sizing: border-box; padding: 0px 5px;">33</li><li style="box-sizing: border-box; padding: 0px 5px;">34</li><li style="box-sizing: border-box; padding: 0px 5px;">35</li><li style="box-sizing: border-box; padding: 0px 5px;">36</li><li style="box-sizing: border-box; padding: 0px 5px;">37</li><li style="box-sizing: border-box; padding: 0px 5px;">38</li><li style="box-sizing: border-box; padding: 0px 5px;">39</li><li style="box-sizing: border-box; padding: 0px 5px;">40</li><li style="box-sizing: border-box; padding: 0px 5px;">41</li><li style="box-sizing: border-box; padding: 0px 5px;">42</li><li style="box-sizing: border-box; padding: 0px 5px;">43</li><li style="box-sizing: border-box; padding: 0px 5px;">44</li><li style="box-sizing: border-box; padding: 0px 5px;">45</li><li style="box-sizing: border-box; padding: 0px 5px;">46</li><li style="box-sizing: border-box; padding: 0px 5px;">47</li><li style="box-sizing: border-box; padding: 0px 5px;">48</li><li style="box-sizing: border-box; padding: 0px 5px;">49</li><li style="box-sizing: border-box; padding: 0px 5px;">50</li><li style="box-sizing: border-box; padding: 0px 5px;">51</li><li style="box-sizing: border-box; padding: 0px 5px;">52</li><li style="box-sizing: border-box; padding: 0px 5px;">53</li><li style="box-sizing: border-box; padding: 0px 5px;">54</li><li style="box-sizing: border-box; padding: 0px 5px;">55</li><li style="box-sizing: border-box; padding: 0px 5px;">56</li><li style="box-sizing: border-box; padding: 0px 5px;">57</li><li style="box-sizing: border-box; padding: 0px 5px;">58</li><li style="box-sizing: border-box; padding: 0px 5px;">59</li></ul><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li><li style="box-sizing: border-box; padding: 0px 5px;">9</li><li style="box-sizing: border-box; padding: 0px 5px;">10</li><li style="box-sizing: border-box; padding: 0px 5px;">11</li><li style="box-sizing: border-box; padding: 0px 5px;">12</li><li style="box-sizing: border-box; padding: 0px 5px;">13</li><li style="box-sizing: border-box; padding: 0px 5px;">14</li><li style="box-sizing: border-box; padding: 0px 5px;">15</li><li style="box-sizing: border-box; padding: 0px 5px;">16</li><li style="box-sizing: border-box; padding: 0px 5px;">17</li><li style="box-sizing: border-box; padding: 0px 5px;">18</li><li style="box-sizing: border-box; padding: 0px 5px;">19</li><li style="box-sizing: border-box; padding: 0px 5px;">20</li><li style="box-sizing: border-box; padding: 0px 5px;">21</li><li style="box-sizing: border-box; padding: 0px 5px;">22</li><li style="box-sizing: border-box; padding: 0px 5px;">23</li><li style="box-sizing: border-box; padding: 0px 5px;">24</li><li style="box-sizing: border-box; padding: 0px 5px;">25</li><li style="box-sizing: border-box; padding: 0px 5px;">26</li><li style="box-sizing: border-box; padding: 0px 5px;">27</li><li style="box-sizing: border-box; padding: 0px 5px;">28</li><li style="box-sizing: border-box; padding: 0px 5px;">29</li><li style="box-sizing: border-box; padding: 0px 5px;">30</li><li style="box-sizing: border-box; padding: 0px 5px;">31</li><li style="box-sizing: border-box; padding: 0px 5px;">32</li><li style="box-sizing: border-box; padding: 0px 5px;">33</li><li style="box-sizing: border-box; padding: 0px 5px;">34</li><li style="box-sizing: border-box; padding: 0px 5px;">35</li><li style="box-sizing: border-box; padding: 0px 5px;">36</li><li style="box-sizing: border-box; padding: 0px 5px;">37</li><li style="box-sizing: border-box; padding: 0px 5px;">38</li><li style="box-sizing: border-box; padding: 0px 5px;">39</li><li style="box-sizing: border-box; padding: 0px 5px;">40</li><li style="box-sizing: border-box; padding: 0px 5px;">41</li><li style="box-sizing: border-box; padding: 0px 5px;">42</li><li style="box-sizing: border-box; padding: 0px 5px;">43</li><li style="box-sizing: border-box; padding: 0px 5px;">44</li><li style="box-sizing: border-box; padding: 0px 5px;">45</li><li style="box-sizing: border-box; padding: 0px 5px;">46</li><li style="box-sizing: border-box; padding: 0px 5px;">47</li><li style="box-sizing: border-box; padding: 0px 5px;">48</li><li style="box-sizing: border-box; padding: 0px 5px;">49</li><li style="box-sizing: border-box; padding: 0px 5px;">50</li><li style="box-sizing: border-box; padding: 0px 5px;">51</li><li style="box-sizing: border-box; padding: 0px 5px;">52</li><li style="box-sizing: border-box; padding: 0px 5px;">53</li><li style="box-sizing: border-box; padding: 0px 5px;">54</li><li style="box-sizing: border-box; padding: 0px 5px;">55</li><li style="box-sizing: border-box; padding: 0px 5px;">56</li><li style="box-sizing: border-box; padding: 0px 5px;">57</li><li style="box-sizing: border-box; padding: 0px 5px;">58</li><li style="box-sizing: border-box; padding: 0px 5px;">59</li></ul>

put方法

<code class="hljs java has-numbering" style="display: block; padding: 0px; color: inherit; box-sizing: border-box; font-family: "Source Code Pro", monospace;font-size:undefined; white-space: pre; border-radius: 0px; word-wrap: normal; background: transparent;">    <span class="hljs-javadoc" style="color: rgb(136, 0, 0); box-sizing: border-box;">/**     * Maps the specified key to the specified value.     *<span class="hljs-javadoctag" style="color: rgb(102, 0, 102); box-sizing: border-box;"> @param</span> key the key.     *<span class="hljs-javadoctag" style="color: rgb(102, 0, 102); box-sizing: border-box;"> @param</span> value the value.     *<span class="hljs-javadoctag" style="color: rgb(102, 0, 102); box-sizing: border-box;"> @return</span> the value of any previous mapping with the specified key or     *         {@code null} if there was no such mapping.     */</span>    <span class="hljs-annotation" style="color: rgb(155, 133, 157); box-sizing: border-box;">@Override</span>     <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> V <span class="hljs-title" style="box-sizing: border-box;">put</span>(K key, V value) {        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (key == <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span>) {<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// HashMap的key是可以为空的,如果为空,放一个NullKey</span>            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">return</span> putValueForNullKey(value);        }        <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 定义一个int型的hash,将key的hashCode计算后再次得到Hash值赋予它,即二次哈希</span>        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> hash = Collections.secondaryHash(key);        HashMapEntry<K, V>[] tab = table;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 存储键值对的数组</span>        <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// index是下标,tab数组长度-1即数组下标最大值,接着做&运算得到下标最大的长度,避免溢出</span>        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> index = hash & (tab.length - <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">1</span>);        <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 遍历索引下面的整个链表,tab[index]整个链表的头结点,如果index索引处的Entry不为 null,通过循环不断遍历e元素的下一个元素  </span>        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">for</span> (HashMapEntry<K, V> e = tab[index]; e != <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span>; e = e.next) {            <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 如果指定key与需要放入的key两个键相同,进行覆盖,新的覆盖老的</span>            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (e.hash == hash && key.equals(e.key)) {                preModify(e);                V oldValue = e.value;                e.value = value;                <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">return</span> oldValue;            }        }        <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 如果index索引处的Entry为null,表明此处还没有 Entry </span>        modCount++;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 计数器++</span>        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (size++ > threshold) {<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 尺寸++大于容量因子的极限,则扩容</span>            tab = doubleCapacity();<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 容量扩大两倍,HashMap容量最小是4,然后两倍两倍的扩容</span>            index = hash & (tab.length - <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">1</span>);<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 重新计算一遍</span>        }        addNewEntry(key, value, hash, index);<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 把新的键值对添加进来</span>        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">return</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span>;    }</code><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li><li style="box-sizing: border-box; padding: 0px 5px;">9</li><li style="box-sizing: border-box; padding: 0px 5px;">10</li><li style="box-sizing: border-box; padding: 0px 5px;">11</li><li style="box-sizing: border-box; padding: 0px 5px;">12</li><li style="box-sizing: border-box; padding: 0px 5px;">13</li><li style="box-sizing: border-box; padding: 0px 5px;">14</li><li style="box-sizing: border-box; padding: 0px 5px;">15</li><li style="box-sizing: border-box; padding: 0px 5px;">16</li><li style="box-sizing: border-box; padding: 0px 5px;">17</li><li style="box-sizing: border-box; padding: 0px 5px;">18</li><li style="box-sizing: border-box; padding: 0px 5px;">19</li><li style="box-sizing: border-box; padding: 0px 5px;">20</li><li style="box-sizing: border-box; padding: 0px 5px;">21</li><li style="box-sizing: border-box; padding: 0px 5px;">22</li><li style="box-sizing: border-box; padding: 0px 5px;">23</li><li style="box-sizing: border-box; padding: 0px 5px;">24</li><li style="box-sizing: border-box; padding: 0px 5px;">25</li><li style="box-sizing: border-box; padding: 0px 5px;">26</li><li style="box-sizing: border-box; padding: 0px 5px;">27</li><li style="box-sizing: border-box; padding: 0px 5px;">28</li><li style="box-sizing: border-box; padding: 0px 5px;">29</li><li style="box-sizing: border-box; padding: 0px 5px;">30</li><li style="box-sizing: border-box; padding: 0px 5px;">31</li><li style="box-sizing: border-box; padding: 0px 5px;">32</li><li style="box-sizing: border-box; padding: 0px 5px;">33</li><li style="box-sizing: border-box; padding: 0px 5px;">34</li><li style="box-sizing: border-box; padding: 0px 5px;">35</li><li style="box-sizing: border-box; padding: 0px 5px;">36</li><li style="box-sizing: border-box; padding: 0px 5px;">37</li></ul><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li><li style="box-sizing: border-box; padding: 0px 5px;">9</li><li style="box-sizing: border-box; padding: 0px 5px;">10</li><li style="box-sizing: border-box; padding: 0px 5px;">11</li><li style="box-sizing: border-box; padding: 0px 5px;">12</li><li style="box-sizing: border-box; padding: 0px 5px;">13</li><li style="box-sizing: border-box; padding: 0px 5px;">14</li><li style="box-sizing: border-box; padding: 0px 5px;">15</li><li style="box-sizing: border-box; padding: 0px 5px;">16</li><li style="box-sizing: border-box; padding: 0px 5px;">17</li><li style="box-sizing: border-box; padding: 0px 5px;">18</li><li style="box-sizing: border-box; padding: 0px 5px;">19</li><li style="box-sizing: border-box; padding: 0px 5px;">20</li><li style="box-sizing: border-box; padding: 0px 5px;">21</li><li style="box-sizing: border-box; padding: 0px 5px;">22</li><li style="box-sizing: border-box; padding: 0px 5px;">23</li><li style="box-sizing: border-box; padding: 0px 5px;">24</li><li style="box-sizing: border-box; padding: 0px 5px;">25</li><li style="box-sizing: border-box; padding: 0px 5px;">26</li><li style="box-sizing: border-box; padding: 0px 5px;">27</li><li style="box-sizing: border-box; padding: 0px 5px;">28</li><li style="box-sizing: border-box; padding: 0px 5px;">29</li><li style="box-sizing: border-box; padding: 0px 5px;">30</li><li style="box-sizing: border-box; padding: 0px 5px;">31</li><li style="box-sizing: border-box; padding: 0px 5px;">32</li><li style="box-sizing: border-box; padding: 0px 5px;">33</li><li style="box-sizing: border-box; padding: 0px 5px;">34</li><li style="box-sizing: border-box; padding: 0px 5px;">35</li><li style="box-sizing: border-box; padding: 0px 5px;">36</li><li style="box-sizing: border-box; padding: 0px 5px;">37</li></ul>

Hash相同,Key不一定相同,如果Key相同,Hash值一定相同。

总结put方法的基本过程如下: 
(1)对key的hashcode进行二次hash计算,获取应该保存到数组中的index。 
(2)判断index所指向的数组元素是否为空,如果为空则直接插入。 
(3)如果不为空,则依次查找e中next所指定的元素,判读key是否相等,如果相等,则替换旧的值,并返回值。 
(4)跳出循环,判断容量是否超出,如果超出进行扩容 
(5)执行addNewEntry()添加方法;

get方法

<code class="hljs java has-numbering" style="display: block; padding: 0px; color: inherit; box-sizing: border-box; font-family: "Source Code Pro", monospace;font-size:undefined; white-space: pre; border-radius: 0px; word-wrap: normal; background: transparent;">    <span class="hljs-javadoc" style="color: rgb(136, 0, 0); box-sizing: border-box;">/**     * Returns the value of the mapping with the specified key.     *<span class="hljs-javadoctag" style="color: rgb(102, 0, 102); box-sizing: border-box;"> @param</span> key the key.     *<span class="hljs-javadoctag" style="color: rgb(102, 0, 102); box-sizing: border-box;"> @return</span> the value of the mapping with the specified key, or {@code null}     *         if no mapping for the specified key is found.     */</span>    <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> V <span class="hljs-title" style="box-sizing: border-box;">get</span>(Object key) {        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (key == <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span>) {<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 如果key为空,把entryForNullKey赋值给e</span>            HashMapEntry<K, V> e = entryForNullKey;            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">return</span> e == <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span> ? <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span> : e.value;        }        <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 根据key的hashCode值计算它的hash码  </span>        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> hash = Collections.secondaryHash(key);        HashMapEntry<K, V>[] tab = table;        <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 直接取出tab数组中指定索引处的值</span>        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">for</span> (HashMapEntry<K, V> e = tab[hash & (tab.length - <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">1</span>)];                e != <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span>; e = e.next) {            <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//拿到每一个键值对中的key</span>            K eKey = e.key;            <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 去比较,如果两个key相等 或者 内存地址相等并且两个哈希值相等,则找到并返回值</span>            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (eKey == key || (e.hash == hash && key.equals(eKey))) {                <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">return</span> e.value;            }        }        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">return</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span>;    }</code><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li><li style="box-sizing: border-box; padding: 0px 5px;">9</li><li style="box-sizing: border-box; padding: 0px 5px;">10</li><li style="box-sizing: border-box; padding: 0px 5px;">11</li><li style="box-sizing: border-box; padding: 0px 5px;">12</li><li style="box-sizing: border-box; padding: 0px 5px;">13</li><li style="box-sizing: border-box; padding: 0px 5px;">14</li><li style="box-sizing: border-box; padding: 0px 5px;">15</li><li style="box-sizing: border-box; padding: 0px 5px;">16</li><li style="box-sizing: border-box; padding: 0px 5px;">17</li><li style="box-sizing: border-box; padding: 0px 5px;">18</li><li style="box-sizing: border-box; padding: 0px 5px;">19</li><li style="box-sizing: border-box; padding: 0px 5px;">20</li><li style="box-sizing: border-box; padding: 0px 5px;">21</li><li style="box-sizing: border-box; padding: 0px 5px;">22</li><li style="box-sizing: border-box; padding: 0px 5px;">23</li><li style="box-sizing: border-box; padding: 0px 5px;">24</li><li style="box-sizing: border-box; padding: 0px 5px;">25</li><li style="box-sizing: border-box; padding: 0px 5px;">26</li></ul><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right; background-color: rgb(238, 238, 238);"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li><li style="box-sizing: border-box; padding: 0px 5px;">9</li><li style="box-sizing: border-box; padding: 0px 5px;">10</li><li style="box-sizing: border-box; padding: 0px 5px;">11</li><li style="box-sizing: border-box; padding: 0px 5px;">12</li><li style="box-sizing: border-box; padding: 0px 5px;">13</li><li style="box-sizing: border-box; padding: 0px 5px;">14</li><li style="box-sizing: border-box; padding: 0px 5px;">15</li><li style="box-sizing: border-box; padding: 0px 5px;">16</li><li style="box-sizing: border-box; padding: 0px 5px;">17</li><li style="box-sizing: border-box; padding: 0px 5px;">18</li><li style="box-sizing: border-box; padding: 0px 5px;">19</li><li style="box-sizing: border-box; padding: 0px 5px;">20</li><li style="box-sizing: border-box; padding: 0px 5px;">21</li><li style="box-sizing: border-box; padding: 0px 5px;">22</li><li style="box-sizing: border-box; padding: 0px 5px;">23</li><li style="box-sizing: border-box; padding: 0px 5px;">24</li><li style="box-sizing: border-box; padding: 0px 5px;">25</li><li style="box-sizing: border-box; padding: 0px 5px;">26</li></ul>

remove方法

<code class="hljs java has-numbering" style="display: block; padding: 0px; color: inherit; box-sizing: border-box; font-family: "Source Code Pro", monospace;font-size:undefined; white-space: pre; border-radius: 0px; word-wrap: normal; background: transparent;">    <span class="hljs-javadoc" style="color: rgb(136, 0, 0); box-sizing: border-box;">/**     * Removes the mapping with the specified key from this map.     *<span class="hljs-javadoctag" style="color: rgb(102, 0, 102); box-sizing: border-box;"> @param</span> key the key of the mapping to remove.     *<span class="hljs-javadoctag" style="color: rgb(102, 0, 102); box-sizing: border-box;"> @return</span> the value of the removed mapping or {@code null} if no mapping     *         for the specified key was found.     */</span>    <span class="hljs-annotation" style="color: rgb(155, 133, 157); box-sizing: border-box;">@Override</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> V <span class="hljs-title" style="box-sizing: border-box;">remove</span>(Object key) {        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (key == <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span>) {<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 如果key等于空,则移除空键值对</span>            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">return</span> removeNullKey();        }        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> hash = Collections.secondaryHash(key);        HashMapEntry<K, V>[] tab = table;        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">int</span> index = hash & (tab.length - <span class="hljs-number" style="color: rgb(0, 102, 102); box-sizing: border-box;">1</span>);        <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 遍历全部结点</span>        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">for</span> (HashMapEntry<K, V> e = tab[index], prev = <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span>;                e != <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span>; prev = e, e = e.next) {            <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 找到结点,如果Hash相等,并且key相等,找到了我们要移除的结点</span>            <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (e.hash == hash && key.equals(e.key)) {                <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">if</span> (prev == <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span>) {<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 遍历到最后结束时找到要删除的结点</span>                    tab[index] = e.next;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 头结点从第二个结点开始算起</span>                } <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">else</span> {<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 在中间任意地方找到了我们要删除的元素</span>                    prev.next = e.next;<span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 这里使用了链表删除元素的套路</span>                }                modCount++;                size--;                postRemove(e);                <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">return</span> e.value;            }        }        <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">return</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">null</span>;    }</code>
0 0
原创粉丝点击