深入解析Java 8中HashMap的底层原理

引言

HashMap是Java中常用的集合类,用于存储键值对。其底层实现经过多次优化,包括哈希算法、数组扩容、链表转红黑树等。本文将深入研究HashMap的底层原理,并详细探讨如何解决哈希碰撞的技术。

1. 哈希算法

HashMap的核心是哈希算法,它通过将键的哈希码映射到数组索引,实现快速的数据查找和插入。在JDK 1.8中,哈希算法经过了一些优化,以提高均匀性和减少碰撞的可能性。

2. 数组与链表结构

HashMap的底层数据结构是一个数组,每个数组元素是一个链表(或红黑树)。当多个键映射到相同的索引位置时,它们将被存储在同一个链表中。为了解决哈希碰撞,链表中存储的是一个个键值对。

3. 键值对的存储

HashMap中,键值对以Node对象的形式存储。每个Node包含键、值、哈希码以及指向下一个Node的引用。当产生哈希冲突时,新的Node将被添加到链表的末尾。

4. 解决哈希碰撞的方法

  1. 链地址法:当发生哈希冲突时,将冲突的元素以链表的形式链接在一起,同一个链表上的元素哈希值相同。
    在这里插入图片描述

  2. 红黑树:当链表长度超过一定阈值(默认为8)时,链表会转换为红黑树,可以减少查找时间。因为红黑树的时间复杂度为O(logn),而链表为O(n)。

  3. 扩容rehash:当HashMap中的元素数量太多,超过数组大小*加载因子时,会发生扩容。扩容后,需要对原数组中的所有元素重新计算哈希值,然后放到新的扩容后的数组中,这样可以增加链表长度,减少哈希冲突。

  4. 优化哈希算法:JDK 1.8中优化了哈希算法,通过hashCode()的高16位异或低16位实现的:(h = k.hashCode()) ^ (h >>> 16),提高了哈希碰撞分布性。

所以Java 8中HashMap主要通过链地址法+红黑树+扩容rehash+优化哈希算法来解决哈希冲突。这些方法相结合可以有效地解决哈希冲突问题,提高HashMap的性能。

5. 数组扩容机制

HashMap中的元素数量超过容量乘以加载因子时,数组会被扩容。在JDK 1.8中,默认加载因子是0.75。扩容涉及到重新计算哈希码、重新分配数组,并将现有元素重新放置到新的数组中。这确保了HashMap的性能和空间的平衡。

6. 红黑树的引入

为了应对链表过长的情况,JDK 1.8引入了红黑树。当链表长度达到8时,链表将被转换为红黑树,以提高查找效率。红黑树的引入使得在最坏情况下,查找时间复杂度从O(n)降低到O(log n)。

为什么当链表长度达到8时,链表将被转换为红黑树,又为什么红黑树转链表的阈值为6?
首先和hashcode碰撞次数的泊松分布有关,主要是为了实现时间和空间的平衡,在负载因子为0.75默认情况下,单个hash槽内元素个数为8的概率小于百万分之一,将7作为一个分水岭,等于7时不做转换,大于等于8才转红黑树,小于等于6才转链表,链表中元素个数为8时的概率已经非常小,再多的就更少了,所以原作者在选择链表元素个数时选择了8,是根据概率统计而选择的,红黑树中的TreeNode,是链表中的Node所占空间的2倍,虽然红黑树的查找效率为o(logN),要优于链表的o(N),但是当链表长度比较小的时候,即使全部遍历,时间复杂度也不会太高,所以,要寻找一种时间和空间的平衡,即在链表长度达到一个阈值,之后再转换为红黑树,之所以是8,是因为Java的源码贡献者,在进行大量实验发现,hash碰撞发生8次的概率,已经降低到了0.00000006,几乎为不可能事件,如果真的碰撞发生了8次,那么这个时候说明由于元素,本身和hash函数的原因,此次操作的hash碰撞的可能性非常大了,后序可能还会继续发生hash碰撞,所以,这个时候,就应该将链表转换为红黑树了,也就是为什么链表转红黑树的阈值是8;
最后,红黑树转链表的阈值为6,主要是因为:如果也将该阈值设置于8,那么当hash碰撞在8时,会反生链表和红黑树的不停相互激荡转换,白白浪费资源。

7. 在Java 8中的实现细节

在JDK 1.8中,HashMap的实现经过了优化,包括更好的哈希算法、红黑树的引入、链表长度的控制等。这些变化使得HashMap在面对各种情况时都能提供高效的性能。

8. 性能优化与注意事项

在使用HashMap时,需要注意一些性能优化的问题,例如合理选择初始容量和加载因子、避免频繁扩容等。对于特定的应用场景,可以通过调整这些参数来达到更好的性能。

结论

HashMap作为Java中常用的数据结构之一,在JDK 1.8中经过了一系列的优化和改进。深入理解其底层原理,包括哈希算法、数组与链表结构、红黑树的引入等,以及如何解决哈希碰撞的技术,有助于更好地使用和理解HashMap的性能特性。在实际应用中,根据具体场景选择适当的参数,可以更好地发挥HashMap的优势,提高程序的性能和效率。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/210110.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

如何搭建Zblog网站并通过内网穿透将个人博客发布到公网

文章目录 1. 前言2. Z-blog网站搭建2.1 XAMPP环境设置2.2 Z-blog安装2.3 Z-blog网页测试2.4 Cpolar安装和注册 3. 本地网页发布3.1. Cpolar云端设置3.2 Cpolar本地设置 4. 公网访问测试5. 结语 1. 前言 想要成为一个合格的技术宅或程序员,自己搭建网站制作网页是绕…

【图文详解】SiamFC++与图注意力的强强联合:单目标追踪系统

1.研究背景与意义 随着计算机视觉技术的不断发展,单目标追踪(Single Object Tracking, SOT)作为计算机视觉领域的一个重要研究方向,已经在许多实际应用中得到了广泛的应用。单目标追踪系统可以通过分析视频序列中的目标运动&…

并行与分布式计算 第9章 算法设计

文章目录 并行与分布式计算 第9章 算法设计9.1 设计过程9.1.1 PCAM设计过程9.1.2 划分9.1.3 通信9.1.4 组合9.1.5 映射 8.2 设计方法8.2.1 划分技术9.2.2 分治9.2.3 平衡树技术9.2.4倍增技术9.2.5 流水线技术9.2.6 破对称技术 并行与分布式计算 第9章 算法设计 9.1 设计过程 …

CFA一二三级24年学习资料

还在持续更新中,要一起学习的话点赞加留言吧。

PTA-用天平找小球

三个球A、B、C,大小形状相同且其中有一个球与其他球重量不同。要求找出这个不一样的球。 输入格式: 输入在一行中给出3个正整数,顺序对应球A、B、C的重量。 输出格式: 在一行中输出唯一的那个不一样的球。 输入样例&#xff…

【深度学习】如何选择神经网络的超参数

1. 神经网络的超参数分类 神经网路中的超参数主要包括: 1. 学习率 η 2. 正则化参数 λ 3. 神经网络的层数 L 4. 每一个隐层中神经元的个数 j 5. 学习的回合数Epoch 6. 小批量数据 minibatch 的大小 7. 输出神经元的编码方式 8. 代价函数的选择 9. 权重初始化的方法 …

哪种小型洗衣机好用?四款公认好用的内衣洗衣机推荐

在近年以来,由于人们对健康的认识和生活质量的不断改善,使得内衣洗衣机这一类的产品在近年来得到了飞速的发展,洗烘一体机、洗烘套装的价格总体下降,功能和性能都得到了改善,往往更多的用户会选择一台或者多台洗衣机来…

安装MySQL搭建论坛

课前默写: 1、nginx配置文件的区域有哪些 ①全局区域 ②events区域 ③http区域 2、区域模块的作用 全局区域模块主要是用户和工作进程 events区域模块配置最大连接数时需先配置:vim /etc/limits.conf 因为系统默认最大是1024 http区域模块:代理地…

补充:如何提高selenium的运行速度?

已经通读该专栏文章的同学,或许对UI自动化测试有了一定的掌握,细心的同学肯定会发现一个问题,当用例量达到一定程度时,对于整体用例的执行速度肯定不会很满意。除了应用多线程运行用例的方式加快速度,有没有其他的方法呢? 今天告诉大家,方法是有的!也是本人新学的。即…

h5如何使用navigateBack回退到微信小程序页面并携带参数

前言 在h5中使用navigateBack回退到微信小程序页面很常见,但是有一种交互需要在回退之后的页面可以得到通知,拿到标识之后,进行某些操作,这样的话,由于微信官方并没有直接提供这样的api,就需要我们开动脑筋…

KT404A远程更换语音芯片方案支持OTA 4G 蓝牙 wifi 物联网

目录 一、简介 2.1 芯片的硬件 2.2 测试的方法 一、简介 KT404A远程更换语音芯片方案支持OTA 4G 蓝牙 wifi 物联网 在线下载的mp3语音芯片ic,通过KT404A的uart直接更换内部的语音文件,从而实现动态的更新语音内容 物联网大潮的来袭。随着智能家居、…

代码随想录刷题】Day17 二叉树04

文章目录 1.【110】平衡二叉树(优先掌握递归)1.1 题目描述1.2 解题思路1.3 java代码实现 2.【257】二叉树的所有路径(优先掌握递归)2.1 题目描述2.2 解题思路2.3 java代码实现 3.【404】左叶子之和(优先掌握递归&#…