在多线程环境下使用哈希表
一.HashTable和HashMap
HashTable是JDK1.0时创建的,其在创建时考虑到了多线程情况下存在的线程安全问题,但是其解决线程安全问题的思路也相对简单:

在其众多实现方法上加上synchronized关键字(效率较低),保证其串行化执行。
但是随着业务场景的多样化,在单线程情况下不需要考虑线程安全问题,于是HashMap应运而生,同理,hashMap没有办法保证线程安全,后面随着多线程情况中的线程安全问题需求不断扩大,在多线程环境下使用哈希表有了新的解决方案。
二.JUC包下的ConcurrentHashMap
我们在这再详细说一下Hashtable存在的弊端:对整个hashtable对象加同一把锁,在多线程情况下,任意两个线程访问Hashtable中的任意数据都会产生锁竞争, size属性也是通过synchronized进行同步的,也是比较慢。同时,一旦触发扩容,该线程完成整个扩容,这个过程涉及到大量元素的拷贝,效率比较低。
ConcurrentHashMap针对这些方面进行了一系列的优化:在读时不加锁,这样大大提高了在hashmap中读取元素的效率,但是需要在元素上加volatile关键字,保证在其元素修改后能第一时间获取,只在写操作上加锁,而且它的加锁方式并不是对整个hashmap对象加锁,而是对‘桶’加锁:对hash表中的每个下标(链表头结点作为锁对象)(提高了锁密度),大大降低了锁冲突的概率。
图示就是由上面这种转化为下面这种


同时利用CAS的特性对size进行更新,效率提高
与此同时还优化了元素的更新策略:化整为零,在进行扩容时,将旧桶中的部分元素搬运到新桶中,在以后调用新桶的方法时再每次搬运部分元素,在这个过程中添加新的元素时直接往新桶中添加,在查找时在两个桶中都进行查找,直到搬运完最后一个元素,再将老桶删除掉(新桶和老桶会同时存在一段时间)
最后我们提出一个问题
concurrentHashMap和HashMap、HashTable之间的区别
①HashMap是线程不安全的
②HashTable线程安全,但是不推荐使用,因为所有的操作都加了synchronized关键字,对性能影响比较大
③ConcurrentHashMap的锁粒度小,不是对整个hash表进行加锁,而是对每一个数据的下标进行加锁
④ConcurrentHashMap对于put()加锁,对于读get()不加锁
⑤对于大量共享变量运行了volatile关键字修饰
⑥对ConcurrentHashMap对扩容进行了优化

相关文章:
在多线程环境下使用哈希表
一.HashTable和HashMapHashTable是JDK1.0时创建的,其在创建时考虑到了多线程情况下存在的线程安全问题,但是其解决线程安全问题的思路也相对简单:在其众多实现方法上加上synchronized关键字(效率较低),保证…...
【排序算法】堆排序(Heap Sort)
堆排序是指利用堆这种数据结构所设计的一种排序算法。堆是一个近似完全二叉树的结构,并同时满足堆积的性质:即子结点的键值或索引总是小于(或者大于)它的父节点。堆排序介绍学习堆排序之前,有必要了解堆!若…...
分类预测 | Matlab实现SSA-RF和RF麻雀算法优化随机森林和随机森林多特征分类预测
分类预测 |Matlab实现SSA-RF和RF麻雀算法优化随机森林和随机森林多特征分类预测 目录分类预测 |Matlab实现SSA-RF和RF麻雀算法优化随机森林和随机森林多特征分类预测分类效果基本介绍模型描述程序设计参考资料分类效果 基本介绍 Matlab实现SSA-RF和RF麻雀算法优化随机森林和随机…...
Allegro如何添加ICT操作指导
Allegro如何添加ICT操作指导 当PCB板需要做飞针测试的时候,通常需要在PCB设计的时候给需要测试的网络添加上ICT。 如图: Allegro支持给网络添加ICT,具体操作如下 首先在库中创建一个阻焊开窗的过孔,比如via10-ict一般阻焊开窗的尺寸比盘单边大2mil 在PCB中选择Manufacture…...
软件架构设计(二)——领域架构、基于架构的软件开发方法
目录 一、架构描述语言 ADL 二、特定领域软件架构 DSSA 三、DSSA的三层次架构模型 . 四、基于架构的软件开发方法 (1)基于架构的软件设计(ABSD) (2)开发过程 一、架构描述语言 ADL ADL是一种形式化语言,它在底层语义模型的支持下,为软件系统概念体…...
数组常用方法(2)---数组遍历方法
1. forEach(cb) 回调函数中有三个参数,第一个是当前遍历项(必须),第二个是索引,第三个是遍历的数组本身。forEach() 对于空数组不会执行回调函数。forEach()不会使用回调函数的返回值,返回值为undefined。…...
卸载Node.js
0 写在前面 无论您是因为什么原因要卸载Node.js都必须要卸载干净。 请阅读: 1 卸载步骤 1.1通过控制面板卸载node.js winR—>control.exe—>卸载程序—>卸载Node.js 等待—>卸载成功 1.2 删除安装时的nodejs文件夹 通过记忆或者Everthing搜索找…...
发表计算机SCI论文,会经历哪些过程? - 易智编译EaseEditing
一、选期刊。 一定要先选期刊。每本期刊都有自己的特色和方向,如果你的稿子已经成型,再去考虑期刊选择的问题,恐怕后期不是退稿就是要大面积修改稿子。 选期刊的标准没有一定的,主要是各单位都有自己的要求,当然小编…...
python中lambda的用法
1. lambada简单介绍 lambda 在Python编程中使用的频率非常高,我们通常提及的lambda表达式其实是python中的一类特殊的定义函数的形式,使用它可以定义一个匿名函数。即当你需要一个函数,但又不想费神去命名一个函数,这时候…...
网络安全协议(3)
作者简介:一名在校云计算网络运维学生、每天分享网络运维的学习经验、和学习笔记。 座右铭:低头赶路,敬事如仪 个人主页:网络豆的主页 目录 前言 一.当前流行操作系统的安全等级 1.Windows的安全等级 什么是EAL…...
102.第十九章 MySQL数据库 -- MySQL的备份和恢复(十二)
5.备份和恢复 5.1 备份恢复概述 5.1.1 为什么要备份 灾难恢复:硬件故障、软件故障、自然灾害、黑客攻击、误操作测试等数据丢失场景 参考链接: https://www.toutiao.com/a6939518201961251359/ 5.1.2 备份类型 完全备份,部分备份 完全备份:整个数据集 部分备份:只备份数…...
【C++】C++入门 类与对象(一)
类与对象(一)一、类的引入二、类的定义1、类的两种定义方式:2、成员变量命名规则的建议:三、类的访问限定符及封装1、访问限定符2、封装四、类的实例化1、类的实例化概念2、类对象的大小的计算五、this指针this指针的特性一、类的…...
笔记_js运算符
目录二进制相关运算符移位运算符<<>>|(位或运算)参考文档二进制相关运算符 移位运算符 移位运算就是对二进制进行有规律的移位。 tips:进制转换文档链接 << “<<”运算符执行左移位运算。在移位运算过程中,符号位始终保持不变…...
java面试题(十九) Mybatis
4.1 谈谈MyBatis和JPA的区别 参考答案 ORM映射不同: MyBatis是半自动的ORM框架,提供数据库与结果集的映射; JPA(默认采用Hibernate实现)是全自动的ORM框架,提供对象与数据库的映射。 可移植性不同&…...
Linux系统位运算函数以及相应CPU ISA实现收录
以32位数据的二进制表示为例,习惯的写法是LSB在左,MSB在右,注意BIT序和大小端的字节序没有关系。Linux和BIT操作有关的接口在定义在头文件bitops.h中,bitops.h定义有两层,通用层和架构层,对应两个bitops.h&…...
logback配置文件---logback.xml
目录常识操作logback-spring.xml 示例参考于 https://blog.csdn.net/white_ice/article/details/85065219 https://blog.csdn.net/weixin_42592282/article/details/122109703 https://www.dianjilingqu.com/629077.html 常识 https://www.dianjilingqu.com/629077.html nod…...
Web前端-设计网站公共header
设计网站公共headerheader元素是一个具有引导和导航作用的结构元素,很多企业网站中都有一个非常重要的header元素,一般位于网页的开头,用来显示企业名称、企业logo图片、整个网站的导航条,以及Flash形式的广告条等。在本网站中&am…...
引用和指针傻傻分不清
🚀🚀🚀大家觉不错的话,就恳求大家点点关注,点点小爱心,指点指点🚀🚀🚀 目录 🐰引用和指针的区别 🌸从现象上看 🌸从编译上看 &am…...
MySQL面试题:关系型数据库SQL和非关系型数据库NoSQL
文章目录一、四大非关系型数据库与关系型数据库的对比1. 关系型数据库2. 基于列的数据库3. 键值对存储4. 文档存储5. 图形数据库参考文章(金文):四大非关系型数据库类型,你知道多少 参考文章:“行式存储”和“列式存储…...
1.Redis【介绍与安装】
1.常用数据库介绍 mysql的表类型[表引擎.存储引擎],memory表结构和表数据分开存储的,表结构保存在硬盘中,表数据保存在内存中memcache是一款软件,可以使用键值对的格式保存数据到内存中redis是意大利的工程师开发的开源免费的告诉缓存数据库,需要注意的是作者本身只开发了linu…...
在HarmonyOS ArkTS ArkUI-X 5.0及以上版本中,手势开发全攻略:
在 HarmonyOS 应用开发中,手势交互是连接用户与设备的核心纽带。ArkTS 框架提供了丰富的手势处理能力,既支持点击、长按、拖拽等基础单一手势的精细控制,也能通过多种绑定策略解决父子组件的手势竞争问题。本文将结合官方开发文档,…...
全球首个30米分辨率湿地数据集(2000—2022)
数据简介 今天我们分享的数据是全球30米分辨率湿地数据集,包含8种湿地亚类,该数据以0.5X0.5的瓦片存储,我们整理了所有属于中国的瓦片名称与其对应省份,方便大家研究使用。 该数据集作为全球首个30米分辨率、覆盖2000–2022年时间…...
MySQL 8.0 OCP 英文题库解析(十三)
Oracle 为庆祝 MySQL 30 周年,截止到 2025.07.31 之前。所有人均可以免费考取原价245美元的MySQL OCP 认证。 从今天开始,将英文题库免费公布出来,并进行解析,帮助大家在一个月之内轻松通过OCP认证。 本期公布试题111~120 试题1…...
HashMap中的put方法执行流程(流程图)
1 put操作整体流程 HashMap 的 put 操作是其最核心的功能之一。在 JDK 1.8 及以后版本中,其主要逻辑封装在 putVal 这个内部方法中。整个过程大致如下: 初始判断与哈希计算: 首先,putVal 方法会检查当前的 table(也就…...
Redis:现代应用开发的高效内存数据存储利器
一、Redis的起源与发展 Redis最初由意大利程序员Salvatore Sanfilippo在2009年开发,其初衷是为了满足他自己的一个项目需求,即需要一个高性能的键值存储系统来解决传统数据库在高并发场景下的性能瓶颈。随着项目的开源,Redis凭借其简单易用、…...
Linux nano命令的基本使用
参考资料 GNU nanoを使いこなすnano基础 目录 一. 简介二. 文件打开2.1 普通方式打开文件2.2 只读方式打开文件 三. 文件查看3.1 打开文件时,显示行号3.2 翻页查看 四. 文件编辑4.1 Ctrl K 复制 和 Ctrl U 粘贴4.2 Alt/Esc U 撤回 五. 文件保存与退出5.1 Ctrl …...
Python Einops库:深度学习中的张量操作革命
Einops(爱因斯坦操作库)就像给张量操作戴上了一副"语义眼镜"——让你用人类能理解的方式告诉计算机如何操作多维数组。这个基于爱因斯坦求和约定的库,用类似自然语言的表达式替代了晦涩的API调用,彻底改变了深度学习工程…...
CVPR2025重磅突破:AnomalyAny框架实现单样本生成逼真异常数据,破解视觉检测瓶颈!
本文介绍了一种名为AnomalyAny的创新框架,该方法利用Stable Diffusion的强大生成能力,仅需单个正常样本和文本描述,即可生成逼真且多样化的异常样本,有效解决了视觉异常检测中异常样本稀缺的难题,为工业质检、医疗影像…...
在树莓派上添加音频输入设备的几种方法
在树莓派上添加音频输入设备可以通过以下步骤完成,具体方法取决于设备类型(如USB麦克风、3.5mm接口麦克风或HDMI音频输入)。以下是详细指南: 1. 连接音频输入设备 USB麦克风/声卡:直接插入树莓派的USB接口。3.5mm麦克…...
Kubernetes 网络模型深度解析:Pod IP 与 Service 的负载均衡机制,Service到底是什么?
Pod IP 的本质与特性 Pod IP 的定位 纯端点地址:Pod IP 是分配给 Pod 网络命名空间的真实 IP 地址(如 10.244.1.2)无特殊名称:在 Kubernetes 中,它通常被称为 “Pod IP” 或 “容器 IP”生命周期:与 Pod …...
