Caffeine中,读操作后的afterRead操作都会异步操作,不会阻塞到正常的读取操作。

在高并发读取的前提下,为每个读取操作的线程建立了专属的buffer来存放afterRead事件由消费者统一处理afterRead事件,避免高并发读取下对于事件写入buffer的时候的资源竞争。

transient volatile Buffer<E>[] table;

StrippedBuffer中维护了一个Buffer[]数组table,用来存放各个线程专属的buffer。

如何界定某个buffer属于哪个线程去写入,又或者如何判断线程在写入的时候应该选择哪个buffer。

static final long PROBE = UnsafeAccess.objectFieldOffset(Thread.class, "threadLocalRandomProbe");
static final int getProbe() {return UnsafeAccess.UNSAFE.getInt(Thread.currentThread(), PROBE);
}

在为每个线程选择具体的buffer的时候,将会根据每个线程的ThreadLocalRandom来hash定位buffer数组的具体位置,每次需要定位的时候通过getProbe()方法,通过Unsafe来获取Thread的threadLocalRandomProbe随机数,通过hash的方式进行定位。

@Override
public int offer(E e) {int mask;int result = 0;Buffer<E> buffer;boolean uncontended = true;Buffer<E>[] buffers = table;if ((buffers == null)|| (mask = buffers.length - 1) < 0|| (buffer = buffers[getProbe() & mask]) == null|| !(uncontended = ((result = buffer.offer(e)) != Buffer.FAILED))) {expandOrRetry(e, uncontended);}return result;
}

当事件具体准备通过offer()方法根据线程的ThreadLocal随机数选择到具体的buffer数组table上的位置,并进行写入。

其中,可能会出现buffer数组没初始化,buffer数组对应位置上的buffer还没初始化完成,buffer由于hash碰撞被并发写入导致一个线程的写入失败,几种情况,这几种情况会通过expandOrRetry()方法进行重试或者扩容。

transient volatile int tableBusy;
final boolean casTableBusy() {return UnsafeAccess.UNSAFE.compareAndSwapInt(this, TABLE_BUSY, 0, 1);
}

在扩容过程中,通过cas修改tablrBusy的量保证线程安全。

caffeine 线程私有的ReadBuffer实现相关推荐

  1. 并发编程02-什么是线程安全以及Java虚拟机中哪些数据是线程共享的,那些是线程私有的

    线程安全的本质 什么是线程安全 要说什么是线程安全,那么我们看看生活中例子吧. 场景1:王菲要来西安体育场开演唱会,这个体育场规模不是很大,能容纳1000个人,于是准备了1000张票,后天中午12点在 ...

  2. 本地方法栈线程公有_Java运行时区域,哪些区域是线程私有的?哪些是共有的?...

    JVM 运行时数据区域大致可以分为:程序计数器.虚拟机栈.本地方法栈.堆区.元空间.运行时常量池.直接内存等区域:就是下面这个样子的: 其中有些区域,随着 JDK 版本的升级不断调整,例如: JDK ...

  3. 聊一聊Spring中的线程安全性

    原文出处:SylvanasSun Spring与线程安全 ThreadLocal ThreadLocal中的内存泄漏 参考文献 Spring与线程安全 Spring作为一个IOC/DI容器,帮助我们管 ...

  4. java线程的优先级是数字越大优先级越高_《深入理解Java虚拟机》5分钟速成:12章(Java内存模型与线程)...

    第12章 Java内存模型与线程 前言: 1.物理机如何处理并发问题? 2.什么是Java内存模型? 3.原子性.可见性.有序性的具体含义和应用实现? 4.volatile 关键字特性? 5.基于vo ...

  5. Spring 中的bean 是线程安全的吗?

    点击上方蓝色"方志朋",选择"设为星标" 回复"666"获取独家整理的学习资料! 作者:myseries cnblogs.com/myser ...

  6. 聊一聊 Spring 中的线程安全性

    点击上方"方志朋",选择"设为星标" 回复"666"获取新整理的面试文章 作者 | SylvanasSun 来源 | juejin.im/p ...

  7. 今天我们来聊一聊 Spring 中的线程安全性

    点击上方"方志朋",选择"设为星标" 回复"666"获取新整理的面试文章 Spring与线程安全 Spring作为一个IOC/DI容器,帮助 ...

  8. controller如何保证当前只有一个线程执行_今天我们来聊一聊 Spring 中的线程安全性...

    优质文章,及时送达 Spring与线程安全 Spring作为一个IOC/DI容器,帮助我们管理了许许多多的"bean".但其实,Spring并没有保证这些对象的线程安全,需要由开发 ...

  9. Spring中的Controller ,Service,Dao是不是线程安全的?

    作者:myseries cnblogs.com/myseries/p/11729800.html 结论:不是线程安全的 Spring容器中的Bean是否线程安全,容器本身并没有提供Bean的线程安全策 ...

最新文章

  1. gcc编译C++程序
  2. 3种团队分组适应项目_业务团队怎样做目标管理?更能激励员工?(附实操方法)...
  3. ruby array_在Ruby中使用Array.delete()和Array.delete_at()从Array中移除元素
  4. Redis的内部运作机制——Redis详解
  5. 视频会议专线部署不会?别急,我教你
  6. 小米总参php面试题_php面试题之二——Javascript(基础部分)
  7. 【笔记】Java数据结构与算法
  8. mysql shell 配置mysql_Windows Mysql shell 配置
  9. jenkins 插件安装
  10. iOS13深色模式/暗黑模式导航栏不自动适配的解决方案
  11. 2019计算机二级vb考试大纲,2019年全国计算机二级VB试题
  12. 《AutoCAD全套园林图纸绘制自学手册》一1.5 园林设计图的绘制
  13. 伺服的电机转矩、功率、转速、电压、电流换算公式
  14. 如何解决word添加脚注后正文跑到下一页的问题
  15. 计算机裸机的功能,计算机中裸机是指什么
  16. BeautyGAN图片的高精度美颜
  17. GraphX 在图数据库 Nebula Graph 的图计算实践
  18. 智能体适能训练评估系统-体姿体态评估系统软件
  19. 关于Alphago zero,是的,我来跟风了
  20. 结构光-----激光散斑图像评测算法

热门文章

  1. 五大react生命周期使用注意事项,绝对干货
  2. Oracle数据库导入csv文件(sqlldr命令行)
  3. VMware客户端vSphereClient新建虚拟机
  4. Eclipse使用技巧
  5. 光源时间_D65光源对色灯箱的操作步骤及作业标准
  6. 今日SGU 5.20
  7. c++101rule
  8. CF(437C)The Child and Toy(馋)
  9. Java中接口定义成员变量
  10. Hibernate(十三)迫切内连接fetch