首页 > 其他分享 >HashMap index 计算以及 map 扩容旧值如何处理

HashMap index 计算以及 map 扩容旧值如何处理

时间:2022-10-13 00:00:27浏览次数:66  
标签:index hash HashMap 17 16 旧值 key oldcap

首先 index 如何计算 

  我们都知道添加一个Entry 进 Map其实就是添加一个不可重复的 key 进入散链表中,

       在计算的时候 首先会获取到 index 的 hash 值 而 hash 值是一个 int 范围内的整数, 而 index 值的范围只能是 在 0  到 cap (筒子个数减一)

  那么就需要将 hash 值缩小 ,通过取余的形式缩小 ,hashmap 是通过  key.hash() & cap  等价于 key.hash() % cap  ,此时 index 的值便被计算出  

       在计算机中 位运算是 远远快于 算数运算的

那么接下来还有一个问题,当扩容后旧值是如何处理的,旧值的新位置在扩容后的哪个桶中

       扩容是如何计算新桶的位置的

       判断 key.hash()& oldcap.size() 是否为 0

       为 0 则证明 key.hash()的值小于 oldcap.size() ,那么自然之前在哪个筒子 现在也在哪个筒子

       不为 0 则证明  key.hash() 的值 大于 oldcap.size(),此时此key 的新位置就是  旧 index + oldcap.size();

       举例说明    比如之前的桶是 16 个  扩容后是 32 个 (由于 hashmap 扩容是 2 的指数倍 所以可以这样计算)

       之前的 hash 值的 7 那么   7 & 16 = 0  ,  并且 7&(16 -1) = 7   , 7&(32 - 1  ) = 7

       之前的 hash 值是 17  那么  17 & 16 = 1,并切 17 & (16 -1 ) = 1, 17 &(32 -1 ) = 17 ,   17 = 1 - 16(oldcap) 

       也就是 扩容后 将桶分为地位和高位 ,之前在地位的 且 hash 值没有 oldcap 大的 还在低位  ,hash 值比 oldcap 大的 那么 新位置就是 旧 index  + oldcap 

那么在扩容后查新值的时候 ,计算的hash 值是不变的  ,但是取模的时候 基数已经是 (现有筒子的个数 -1) ,同样 index  值还是可以被正确的取到的 

 

 

汲取地址  https://blog.csdn.net/qq_37155154/article/details/115161022

标签:index,hash,HashMap,17,16,旧值,key,oldcap
From: https://www.cnblogs.com/haodongshuai/p/16786592.html

相关文章

  • Java HashMap
    importjava.util.HashMap;/***JavaHashMap*HashMap是一个散列表,它存储的内容是键值对(key-value)映射。**HashMap实现了Map接口,根据键的HashCode值存储数据,......
  • PostgreSQL Create Index Concurrently
    PostgreSQL支持在线创建索引(CREATEINDEXCONCURRENTLY),不堵塞其他会话对被创建索引表的DML(INSERT,UPDATE,DELETE)操作。PostgreSQL提供了一个创建索引的高效特性,即“并发......
  • HashMap实现原理及源码分析
    哈希表(hashtable)也叫散列表,是一种非常重要的数据结构,应用场景及其丰富,许多缓存技术(比如memcached)的核心其实就是在内存中维护一张大的哈希表,而HashMap的实现原理也常常出现......
  • ConcurrentHashMap底层原理
    5.6ConcurrentHashMap底层原理5.6.1jdk1.75.6.1.1数组结构数据结构是数组+segment对象,采用segment分段锁和CAS保证并发。5.6.1.2put操作流程/***Co......
  • WPF listbox中添加index
    关键代码:如果中在ItemsControl中加入Index,"RelativeSource={RelativeSourceAncestorType=ListBoxItem}"可以写成,"RelativeSource={RelativeSourceTemplatedParent}"但是......
  • Java HashMap getOrDefault() 方法
    参考链接:https://www.runoob.com/java/java-hashmap-getordefault.htmlhttps://blog.csdn.net/weixin_43263961/article/details/86513880......
  • IfcSegmentIndexSelect
    IfcSegmentIndexSelect类型定义IfcSegmentIndexSelect提供指向点列表的不同索引列表的选择。注:选择类型用于IfcIndexedPolyCurve指向IfcCartesianPointList,以提供多段曲......
  • HashMap 源码学习
    HashMap1、总体架构2、方法源码2.1hash()方法这里进行了一次扰动计算,hash值右移16位高位也参加运算,增大随机性。  2.2构造方法()https://www.cnblogs.com/xiyix......
  • HashMap 源码,看我这篇就够了
    HashMap源码,看我这篇就够了HashMap源码深度剖析*HashMap底层数据结构(为什么引入红黑树、存储数据的过程、哈希碰撞相关问题)*HashMap成员变量(初始化容量是多少、......
  • HashMap 源码,看我这篇就够了
    HashMap源码,看我这篇就够了HashMap源码深度剖析*HashMap底层数据结构(为什么引入红黑树、存储数据的过程、哈希碰撞相关问题)*HashMap成员变量(初始化容量是多少......