HashMap源码解析
hashmap的数结构
(1)在Java中,数据结构分为两种,一种是数组,另一个是模型指针即引用,所有的数据结构都可以用这两种基本结构所构造,HashMap就是一个数组和链表的结合体,即通过hashcode找到数组中的某一个元素,然后通过key的equals方法在链表中找到key的位置对应的value。
(2)当创建一个hashmap的时候,就会初始化一个entry的数组,每一个entry的数组元素会持有一个指向下一个元素的引用,这就构成了链表。当我们往hashmap中put元素的是时候,先跟住key的hash值得到这个元素在数组中的位置(即下标)然后可以把这个元素放在对应的位置之中了,如果这个位置继续放其他的元素,那么在同一个位子上的元素将以链表的形式存放,新加入的放在链头,最先加入的就会放在链未,从hashmap之中get元素的时候,首先计算hashmap的key值得hashcode,找到数组中对应位置的某一个元素,然后通过key的equals方法在对应的位置的链表中找到需要的元素,其实也就是说,如果每一个链表的位置只有一个元素,那么hashmap的get的效率是最高的。
hash算法
(1)首先先算的key的hashcode的值,然后和数组长度-1做一次&,这样就可以保证得到与数组index相同的几率较小,那么数据在数组上分布的就比较均匀,也就是碰撞率较小,响应的提高了查询的效率。
hashmap的扩容
(1)当hashmap中的元素越来越多的时候,碰撞的几率就会直线上升,为了提高查询的效率,就要对hashmap的数组进行扩容,而在hashmap数组扩容时候,原数组中的数据必须重新计算其在新数组中的位置,并放进去,这个过程叫resize,而这个过程十分耗时,所以说,尽量在声明的时候,就定义它的大小。
hashmap 源码解析
(1)hashmap的数据存储结构
transient Entry[] table
hashmap中的key-value都是存在entry数组中的
(2)数据节点entry的数据结构
entry是一个单向的链表,entr,实现了map.entry 的接口,即实现了getkey(),getvalue(),setvalue()
,equals(),hashcode()等这些函数,这些都是基本的读取/修改key、value 值的函数。
(3)hashmap的构造函数
(1. 默认构造函数 hashmap();
(2. 指定容量大小和加载因子的构造函数 hashmap(int initalcapaciry,float loadFactor)
(3. 指定容量大小的构造函数 hashmap(int initialcapacity)
(4. 包含map的构造函数 hashmap(map<? extends K,? extends V> m)
(4) clear()
clear()的作用是清空hashmap,它是通过将所有的元素设置为null来实现的。
(5)containsKey()
containsKey()的作用是判断hashmap是否包含key
(6)containsValue()
containsValue()的作用是判断hashmap是否包含值为value的元素