HashMap理解
HashMap
Java8 对 HashMap 进行了一些修改,最大的不同就是利用了红黑树,所以其由 数组+链表+红黑
树 组成。
当链表中的元素超过了 8 个以后, 会将链表转换为红黑树
HashMap扩容机制#
capacity 即容量,默认16。
loadFactor 加载因子,默认是0.75
threshold 阈值。阈值=容量*加载因子。默认12。当元素数量超过阈值时便会触发扩容。
- 空参数的构造函数:实例化的HashMap默认内部数组是null,即没有实例化。第一次调用put方法时,则会开始第一次初始化扩容,长度为16。
- 有参构造函数:用于指定容量。会根据指定的正整数找到不小于指定容量的2的幂数,将这个数设置赋值给阈值(threshold)。第一次调用put方法时,会将阈值赋值给容量,然后让
。(因此并不是我们手动指定了容量就一定不会触发扩容,超过阈值后一样会扩容!!)
- 如果不是第一次扩容,则容量变为原来的2倍,阈值也变为原来的2倍。(容量和阈值都变为原来的2倍时,负载因子还是不变)
为什么HashMap的长度是2的整数次幂?#
为了加快哈希计算以及减少哈希冲突
要决定元素的存储位置,先得算出元素的hash,然后hash & (length-1)得到结果
如果length-1是2的次幂,那么转换成2进制就全是1
而hash & 111··· 不容易出现重复的值,从而减少哈希冲突
ConcurrentHashMap
Segment 段#
ConcurrentHashMap 和 HashMap 思路是差不多的,但是因为它支持并发操作,所以要复杂一
些。整个 ConcurrentHashMap 由一个个 Segment 组成,Segment 代表”部分“或”一段“的
意思,所以很多地方都会将其描述为分段锁。注意,行文中,我很多地方用了“槽”来代表一个
segment。
线程安全(Segment 继承 ReentrantLock 加锁)#
简单理解就是,ConcurrentHashMap 是一个 Segment 数组,Segment 通过继承
ReentrantLock 来进行加锁,所以每次需要加锁的操作锁住的是一个 segment,这样只要保证每
个 Segment 是线程安全的,也就实现了全局的线程安全。
!
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南