concurrenthashmap jdk1.8
参考:https://www.jianshu.com/p/c0642afe03e0
CAS的思想很简单:三个参数,一个当前内存值V、旧的预期值A、即将更新的值B,当且仅当预期值A和内存值V相同时,将内存值修改为B并返回true,否则什么都不做,并返回false。
细节参考:https://www.jianshu.com/p/fb6e91b013cc
参考:http://blog.csdn.net/u010412719/article/details/52145145
https://www.jianshu.com/p/c0642afe03e0
总结:CAS操作就是将内存中的值和预期中的值比较,相等则修改,并返回true,不相等返回false
casTabAt(Node<K,V>[] tab, int i, Node<K,V> c, Node<K,V> v) (将c与tab[i]比较)设置节点上的值
相对于synchronized操作要更快。
concurrenthashmap在jdk中1.8中利用CAS+Synchronized来保证并发更新的安全,没有利用segment分段锁的机制。
concurrentHashMap扩容
1、put新增一个节点,计算hash值。
检验entry数据是否初始化?没有,那么初始化initTable
检验table[i]是否为null?为null,利用cas添加节点
不为null,判断是否在扩容?在扩容帮助扩容,没有则helpTransfer帮助扩容
以上情况均不符合,synchronized锁定头节点,判断为链表节点,则插入链表的尾部
判断为树节点,则按照树添加节点
如果元素>=8?转化为树{
如果数组<64,扩容,只有当sizeCtl>0,才能扩容trasfer方法
如果数组>64,转化为树
}
2、扩容
情况1:当元素新增字节后,链表个数到达8,就会调用treeifBin把链表转化为
红黑树。在转化之前,如果数组长度小于阈值MIN_TREEIFY_CAPACITY,默认是64,
就会调用treePresize方法将数组扩大到原来的两倍。触发transfer方法,调整节点
的位置。
情况2:新增节点后,调用addCount方法记录元素个数,当达到阈值时就会调用transfer扩容
如果槽点为链表,由于是扩大到原来的两倍,transfer中就会利用fn&n快速将链表中的元素分为两类,分别生成一个和最后一节点fn&n相同的顺序列表,一个和最后一节点fn&n不同的反序列表,通过CAS把两者存储在新的数组中。
如果槽位为红黑树,则构造两个树节点,遍历红黑树,同样根据hash&n把节点分为两类,插入两个树节点的链表中。如果链表小于等于UNTREEIFY_THRESHOLD(6),则转化为普通列表。如果另一个节点的长度为0,那么将原始红黑树取过来。不然就根据链表重新创建树。最后通过CAS存储到新的数组中。
3、get
1、判断table是否为空,为空直接返回null
2、计算keyhash值,通过tabAt获得制定点的node,然后遍历链表或者树结构找到对应的点返回value
4、size
通过mappingCount获取size,主要时利用long替代int
但是两者计算出来都是一个估值,并没有像jdk1.7那样不断循环计算准确值
setTabAt(Node<K,V>[] tab, int i, Node<K,V> v){
//设置obj对象中offset偏移地址对应的object型field的值为指定值
U.putObjectVolatile(tab, ((long)i << ASHIFT) + ABASE, v);
}上锁时,设置节点上的值
tabAt(Node<K,V>[] tab, int i) 获取索引处node,保证读到最新对象
concurrenthashmap jdk1.8的更多相关文章
- ConcurrentHashMap(JDK1.8)为什么要放弃Segment
今天看到一篇博客:jdk1.8的HashMap和ConcurrentHashMap,我想起了前段时间面试的一个问题:ConcurrentHashMap(JDK1.8)为什么要使用synchronize ...
- Java泛型底层源码解析--ConcurrentHashMap(JDK1.7)
1. Concurrent相关历史 JDK5中添加了新的concurrent包,相对同步容器而言,并发容器通过一些机制改进了并发性能.因为同步容器将所有对容器状态的访问都串行化了,这样保证了线程的安全 ...
- 多线程-ConcurrentHashMap(JDK1.8)
前言 HashMap非线程安全的,HashTable是线程安全的,所有涉及到多线程操作的都加上了synchronized关键字来锁住整个table,这就意味着所有的线程都在竞争一把锁,在多线程的环境下 ...
- 6.ConcurrentHashMap jdk1.7
6.1 hash算法 就是把任意长度的输入,通过散列算法,变换成固定长度的输出,该输出就是散列值.这种转换是一种压缩映射,也就是,散列值的空间通常远小于输入的空间,不同的输入可能会散列成相同的输出,所 ...
- Java并发编程总结4——ConcurrentHashMap在jdk1.8中的改进(转)
一.简单回顾ConcurrentHashMap在jdk1.7中的设计 先简单看下ConcurrentHashMap类在jdk1.7中的设计,其基本结构如图所示: 每一个segment都是一个HashE ...
- Java并发编程总结4——ConcurrentHashMap在jdk1.8中的改进
一.简单回顾ConcurrentHashMap在jdk1.7中的设计 先简单看下ConcurrentHashMap类在jdk1.7中的设计,其基本结构如图所示: 每一个segment都是一个HashE ...
- ConcurrentHashMap原理分析(1.7与1.8)
前言 以前写过介绍HashMap的文章,文中提到过HashMap在put的时候,插入的元素超过了容量(由负载因子决定)的范围就会触发扩容操作,就是rehash,这个会重新将原数组的内容重新hash到新 ...
- 并发容器和框架之ConcurrentHashMap
了解HashMap的人都知道HashMap是线程不安全的(多线程下的put方法达到一定大小,引发rehash,导致闭链,最终占满CPU),同时线程安全的HashTable效率又令人望而却步(每个方法都 ...
- 深入解析ConcurrentHashMap类
以前写过介绍HashMap的文章,文中提到过HashMap在put的时候,插入的元素超过了容量(由负载因子决定)的范围就会触发扩容操作,就是rehash,这个会重新将原数组的内容重新hash到新的扩容 ...
随机推荐
- 论文翻译第二弹--用python(或Markdown)对论文复制文本进行处理
图中这种论文你想进行文本复制放入翻译软件进行翻译时,会发现是这种形式: 句子之间是断开的,这时普遍的方法,也是我之前一直用的方法就是打开一个文档编辑器,复制上去后一行行地继续调整.昨天不想这样了,就打 ...
- 记springboot+mybatis+freemarker+bootstrap的使用(2)
二.springboot+mybatis的使用 1.springboot的注解:@SpringBootApplication :启动项目:整合常用注解(@Configuration,@EnableAu ...
- TCP/IP协议族、版本以及编址机制
TCP/IP协议族简称TCP/IP.这么命名是因为该协议家族中的两个核心协议:TCP(传输控制协议)和IP(网际协议),为该家族中最早通过的标准.TCP/IP提供点对点的链接机制,将数据应该如何封装, ...
- 成都Uber优步司机奖励政策(3月29日)
滴快车单单2.5倍,注册地址:http://www.udache.com/ 如何注册Uber司机(全国版最新最详细注册流程)/月入2万/不用抢单:http://www.cnblogs.com/mfry ...
- [python3.x]win 7 下Pyinstaller库的安装与使用---探索之路
一.下载安装包 cmd进入命令行,执行命令:pip install https://github.com/pyinstaller/pyinstaller/archive/develop.tar.gz ...
- #386. 【UNR #3】鸽子固定器
#386. [UNR #3]鸽子固定器 题目链接 官方题解 分析: 神奇的做法+链表. 首先按照大小排序. 对于小于选择小于m个物品的时候,这个m个物品一定是一段连续的区间.因为,如果中间空着一个物品 ...
- Mysql 8.0.* zip版本 windows安装
一,MySQL8.0.*zip版本安装步骤. 1,下载 https://dev.mysql.com/get/Downloads/MySQL-8.0/mysql-8.0.15-winx64.zip 注现 ...
- hdu1106 排序(字符串分割,strtok+sscanf)
排序 Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)Total Submissi ...
- MySQL☞关联查询
关联查询:所需要的数据来源于多张表,通过表的连接查询(关联查询)来查询多张表中的数据 格式: select 别名1 . */列名 , 别名2 . */列名 from 表名1 别名1 , 表名2 别 ...
- 第八模块:算法&设计模式、企业应用 第2章 企业应用工具学习
第八模块:算法&设计模式.企业应用 第2章 企业应用工具学习