HashMap和ConcurrentHashMap 源码关键点解析
第一部分:关键源码讲解
1.HashMap 是如何存储的?
a.底层是一个数组 tab
b. hash=hash(key) ,然后根据数组长度n和hash值,决定当前需要put的元素对应的数组下标,
hash算法见红框。

2.数组长度是固定的,HashMap 可以无限put(k,v) ,为什么?
HashMap 的元素个数大于threshold的时候,会进行resize() 扩容

3.如何实现扩容的?
扩容就是通过 resize() , 重新创建一个新数组,对所有元素rehash,放到新数组相应位置。
扩容代价是很大的,所以很多公司编码规范都有一条,合理设置hashMap的InitialCapicity,
禁止直接用HashMap()

4.Hash 冲突是什么?怎么解决这个问题?
Hash 冲突: 假如一个学校有366个同学,一年365天,那么至少有两个同学是同一天生日,这就是hash冲突。用代码来说,不同的key 经过计算p = tab[i = (n - 1) & hash] 对应同一个p
如何解决:
p在有的翻译文档中叫桶,一个桶可以装多个,怎么装? 链表或者红黑树。

以上代码中 else if 部分是红黑树
else 部分是链表 ,链表中如果冲突元素个>=TREEIFY_THRESHOLD-1,会将链表转换成红黑树。
因为元素个数很多时,红黑树比链表性能更好。
5.HashMap 是不是线程安全的,如何解决线程安全问题?

答案是NO,如何解决:
a.对整个map加锁。
b.直接用ConcurrentHashMap

对f加锁了,就是对桶加锁,就是传说中的分段锁机制。
在保证安全的前提下,加锁的范围越小,则程序性能越高,自己写代码时切记胡乱在方法上加synchronized
6.HashMap 和 hash() equals() 方法的关系
面试中面试官会问重写equals()方法要注意是什么,答案是hash()也要重写。
不重写会引起HashMap 等集合类使用的混乱。

比如类Person(id,name),重写了 equals(Object obj){... reutrn this.id==obj.id},没有重写hash(), 那么从类定义上来说,只要id相等就是同一个人,当我们Person作为key,放入两个Person对象(id相等)到HashMap的时候,那么就翻车了,HashMap 会有两个元素,而我们期望的只保留一个。
第二部分:实验验证
1.验证ConcurrentHashMap 线程安全。


2.重写equals()不重写hash() 翻车问题验证。
需要源码或者需要系列文章更新通知,请加微信 kevinzhang7234
转自: http://skycity.today/?thread-38.htm
HashMap和ConcurrentHashMap 源码关键点解析的更多相关文章
- HashTable、HashMap与ConCurrentHashMap源码解读
HashMap 的数据结构 hashMap 初始的数据结构如下图所示,内部维护一个数组,然后数组上维护一个单链表,有个形象的比喻就是想挂钩一样,数组脚标一样的,一个一个的节点往下挂. 我们可以 ...
- HashMap TreeMap ConcurrentHashMap 源码
1 HashMap java se 1.6 1.1 父类 java.lang.Object 继承者 java.util.AbstractMap<K,V> 继承者 java.util.Has ...
- Java 集合系列 09 HashMap详细介绍(源码解析)和使用示例
java 集合系列目录: Java 集合系列 01 总体框架 Java 集合系列 02 Collection架构 Java 集合系列 03 ArrayList详细介绍(源码解析)和使用示例 Java ...
- Java 集合系列10之 HashMap详细介绍(源码解析)和使用示例
概要 这一章,我们对HashMap进行学习.我们先对HashMap有个整体认识,然后再学习它的源码,最后再通过实例来学会使用HashMap.内容包括:第1部分 HashMap介绍第2部分 HashMa ...
- 数据结构算法 - ConcurrentHashMap 源码解析
五个线程同时往 HashMap 中 put 数据会发生什么? ConcurrentHashMap 是怎么保证线程安全的? 在分析 HashMap 源码时还遗留这两个问题,这次我们站在 Java 多线程 ...
- Java之ConcurrentHashMap源码解析
ConcurrentHashMap源码解析 目录 ConcurrentHashMap源码解析 jdk8之前的实现原理 jdk8的实现原理 变量解释 初始化 初始化table put操作 hash算法 ...
- JDK1.7 ConcurrentHashMap 源码浅析
概述 ConcurrentHashMap是HashMap的线程安全版本,使用了分段加锁的方案,在高并发时有比较好的性能. 本文分析JDK1.7中ConcurrentHashMap的实现. 正文 Con ...
- mybatis 3.x源码深度解析与最佳实践(最完整原创)
mybatis 3.x源码深度解析与最佳实践 1 环境准备 1.1 mybatis介绍以及框架源码的学习目标 1.2 本系列源码解析的方式 1.3 环境搭建 1.4 从Hello World开始 2 ...
- 死磕 java集合之ConcurrentHashMap源码分析(三)
本章接着上两章,链接直达: 死磕 java集合之ConcurrentHashMap源码分析(一) 死磕 java集合之ConcurrentHashMap源码分析(二) 删除元素 删除元素跟添加元素一样 ...
随机推荐
- JAVA遇见HTML——JSP篇(JavaBeans)
1.像使用普通java类一样,创建javabean实例,利用构造方法创建实例 跟表单关联,“*”表示根据名称来进行匹配,就是根据表单所提交过来的参数的名字和Javabean当中的属性名字来进行一一匹配 ...
- CCPC 2016 杭州 E. Master of Subgraph(点分治+bitset优化DP)
题目链接:http://acm.hdu.edu.cn/downloads/CCPC2018-Hangzhou-ProblemSet.pdf 题意:给定一棵有 n 个结点的树和一个数 m,对于 i ∈ ...
- 15分钟入门Markdown
一.标题一 标题三 标题六 # 一.标题一 ### 标题三 ###### 标题六 二.字体 1.普通字体 字体加粗 斜体 斜体加粗 删除线 1.普通字体 **字体加粗** *斜体* ***斜体加粗** ...
- python执行ad_hoc
import shutil from collections import namedtuple from ansible.parsing.dataloader import DataLoader f ...
- 【极大化剪枝】Power Hungry Cows-C++【没有用A*!】【超级简单!】
Description小KITTY想要快速计算整数P的幂 (1 <= P <=10,000),它们需要你的帮助.因为计算极大数的幂,所以它们同一时间仅能使用2个存储器,每个存储器可记录某个 ...
- Maxim-可自定义的Monkey测试工具(Android)
Maxim 基于monkey做的二次开发,相比原始monkey,新增如下功能 多种随机测试模式:dfs(深度遍历) mix模式(monkey随机测试+控件识别) troy模式(按照控件选择器进行遍历) ...
- spring事务配置异常
spring事务配置不回滚spring事务管理配置,一般来说都是可以回滚的,最近在开发的过程中遇到了一个异常不回滚的问题,最终找到了原因,贴出来一下 1.首先这里定义一个接口 在接口中定义几个方法 2 ...
- G-LAB四月份作业-数据可视化问题探讨
G-LAB四月份作业-数据可视化问题探讨 引子: 数据平台项目建设正在按照公司的计划开展执行中,作为平台建设项目参与者之一,感觉目前我们现有的MIS报表平台数据也不可谓不丰富,但是不论从提供给用户的数 ...
- 消灭WinRAR广告
1. 问题描述 WinRAR每次弹出的广告真的令人厌烦至极,虽然软件公司也得恰饭,免费给你用总得看俩广告吧,但是像我这样经常用WinRAR的人来说广告弹出频率未免也太过分了.一开始还只是用火绒的弹窗拦 ...
- xman随机数相关题目
参加xman夏令营,大佬给我们带来了密码学课程.其中随机数部分感受颇深,记录下几个脚本. 1. 以时间作为种子的随机数 https://www.jarvisoj.com/ 的[xman2019]bab ...