《Java并发编程实战》中的VolatileCachedFactorizer展示了如何使用volatile和不可变性来实现线程安全。解决了简单缓存实现中可能出现的线程安全问题,同时避免了全量同步带来的性能开销。

场景背景

假设有一个服务(如因数分解服务),需要缓存最近的计算结果以提高效率:

  • 当新请求的参数与缓存中的参数相同时,直接返回缓存结果。
  • 当参数不同时,重新计算并更新缓存。

核心挑战:如何在多线程并发访问时,保证缓存读写的线程安全,同时减少同步开销

代码实现与核心思路

VolatileCachedFactorizer的关键实现如下:

@ThreadSafe
public class VolatileCachedFactorizer implements Servlet {// 用volatile修饰缓存的"不可变结果对象"private volatile ImmutableCache cache = new ImmutableCache(null, null);@Overridepublic void service(ServletRequest req, ServletResponse resp) {BigInteger i = extractFromRequest(req);BigInteger[] factors = cache.getFactors(i);// 缓存未命中,重新计算并更新缓存if (factors == null) {factors = factor(i);// 创建新的不可变对象替换旧缓存cache = new ImmutableCache(i, factors);}encodeIntoResponse(resp, factors);}// 不可变的缓存对象private static class ImmutableCache {private final BigInteger lastNumber;private final BigInteger[] lastFactors;public ImmutableCache(BigInteger lastNumber, BigInteger[] lastFactors) {this.lastNumber = lastNumber;// 防御性拷贝,避免外部修改内部数组this.lastFactors = lastFactors != null ? Arrays.copyOf(lastFactors, lastFactors.length) : null;}// 检查缓存是否命中public BigInteger[] getFactors(BigInteger i) {if (lastNumber == null || !lastNumber.equals(i)) {return null;}// 返回拷贝,避免外部修改内部状态return Arrays.copyOf(lastFactors, lastFactors.length);}}// 其他辅助方法(提取参数、因数分解、编码响应)private BigInteger extractFromRequest(ServletRequest req) { ... }private BigInteger[] factor(BigInteger i) { ... }private void encodeIntoResponse(ServletResponse resp, BigInteger[] factors) { ... }
}

线程安全的核心设计

1. 不可变对象消除了 “写冲突”

ImmutableCache是不可变的(所有成员变量用final修饰,且无修改方法):

  • 一旦创建,其内部状态(lastNumberlastFactors)就无法被修改。
  • 任何 “更新缓存” 的操作,本质上都是创建一个新的ImmutableCache对象,而非修改原有对象。

这就从根本上避免了多线程同时修改同一对象的问题 —— 因为根本没有 “修改” 行为,只有 “替换” 对象引用的操作。

2. volatile 保证了 “读可见性”

cache变量用volatile修饰,确保了:

  • 当一个线程创建新的ImmutableCache并赋值给cache时,这个更新会被立即同步到主内存
  • 其他线程读取cache时,会从主内存获取最新值,而非使用本地缓存的旧值。

因此,线程不会读取到 “过期” 的缓存对象,保证了共享状态的可见性。

3. 无锁设计避免了 “同步竞争”

synchronized等锁机制不同,这个实现:

  • 读取缓存时完全无锁,多个线程可以同时安全访问cache(因为对象不可变,读操作本身不会有冲突)。
  • 更新缓存时仅通过 “创建新对象 + 替换引用” 实现,这个操作是原子的(引用赋值在 Java 中是原子操作)。

虽然可能出现 “多个线程同时计算并覆盖缓存” 的情况(导致临时的重复计算),但这种情况不会破坏线程安全 —— 最终缓存会是某个线程计算的正确结果,且所有线程最终都会看到这个最新结果。

可能的问题与局限性

  • 缓存覆盖问题:如果两个线程同时发现缓存未命中,会同时计算并先后更新缓存,后更新的结果会覆盖先更新的,可能导致短暂的“缓存失效”(但不影响线程安全,只是效率略有损失)。
  • 不适合复杂缓存逻辑:仅适用于“单键单值”的简单缓存场景,无法处理缓存过期、LRU淘汰等复杂策略。
  • 依赖不可变性:若ImmutableCache设计不当(如未做防御性拷贝),则会破坏线程安全性。

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

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

相关文章

Linux x86 stability和coredump

1 POSIX pthread_create原理 1)fork()、pthread_create()、vfork()对应的系统调用分别是sys_fork()、sys_clone()、sys_vfork(),它们在内核中都是通过do_fork()实现的。 2)系统中所有的进程都组织在init_task.tasks链表下面,每个进…

【PyTorch】多对象分割

对象分割任务的目标是找到图像中目标对象的边界。实际应用例如自动驾驶汽车和医学成像分析。这里将使用PyTorch开发一个深度学习模型来完成多对象分割任务。多对象分割的主要目标是自动勾勒出图像中多个目标对象的边界。 对象的边界通常由与图像大小相同的分割掩码定义&#xf…

RabbitMQ---面试题

总结我们所学内容,这里推荐博客进行复习 RabbitMQ---面试题_rabbitmq常问面试题-CSDN博客

MasterGo自动布局(Auto Layout)

自动布局是用来表示 子元素与子元素之间互相影响的一种排版方式,是一种响应式布局技术。一般是将所有元素设计完成后再使用自动布局进行设置。 自动布局就是响应式布局,就是在不同尺寸的手机上宽度不同都应该怎么展示。 一般页面的一级元素使用约束进行相对定位,二级元素及里…

还在重启应用改 Topic?Spring Boot 动态 Kafka 消费的“终极形态”

场景描述: 你的一个微服务正在稳定地消费 Kafka 的 order_topic。现在,上游系统为了做业务隔离,新增加了一个 order_topic_vip,并开始向其中投递 VIP 用户的订单。你需要在不重启、不发布新版本的情况下,让你现有的消费…

使用vllm部署neo4j的text2cypher-gemma-2-9b-it-finetuned-2024v1模型

使用vllm部署neo4j的text2cypher-gemma-2-9b-it-finetuned-2024v1模型 系统环境准备 由于使用的基于 nvcr.io/nvidia/cuda:12.1.1-cudnn8-runtime-ubuntu22.04 的 workbench,需要进行以下准备(其他系统环境可忽略) ldconfig -p | grep libcudnn 找到 libcudnn 的so库,然…

Coze源码分析-资源库-创建知识库-前端源码-核心组件

概述 本文深入分析Coze Studio中用户创建知识库功能的前端实现。该功能允许用户在资源库中创建、编辑和管理知识库资源,为开发者提供了强大的知识管理和数据处理能力。通过对源码的详细解析,我们将了解从资源库入口到知识库配置弹窗的完整架构设计、组件…

基于时空数据的网约车订单需求预测与调度优化

一、引言随着共享出行行业的蓬勃发展,网约车已成为城市交通的重要组成部分。如何精准预测订单需求并优化车辆调度,是提升平台运营效率、改善用户体验的关键。本文提出一种基于时空数据的网约车订单需求预测与调度优化方案,通过网格化城市空间…

数据结构 Java对象的比较

在Java中&#xff0c;凡是涉及到比较的&#xff0c;可以分为两类情况&#xff1a;一类是基本数据类型的比较&#xff0c;另一类是引用数据类型的比较。对于基本数据类型的比较&#xff0c;我们通过关系运算符&#xff08;、>、<、!、>、<&#xff09;进行它们之间的…

企智汇建筑施工项目管理系统:全周期数字化管控,赋能工程企业降本增效!​建筑工程项目管理软件!建筑工程项目管理系统!建筑项目管理软件企智汇软件

在建筑施工行业&#xff0c;项目进度滞后、成本超支、质量安全隐患频发、多方协同不畅等问题&#xff0c;一直是制约企业发展的痛点。传统依赖人工记录、Excel 统计的管理模式&#xff0c;不仅效率低下&#xff0c;更易因信息断层导致决策失误。企智汇建筑施工项目管理系统凭借…

k8s-临时容器学习

临时容器学习1. 什么是临时容器2. 实验1. 什么是临时容器 在官网&#xff1a;https://kubernetes.io/zh-cn/docs/concepts/workloads/pods/ephemeral-containers/ 中有介绍 临时容器是用于调试Pod中崩溃的容器或者不具备调试工具&#xff0c;比如在一个运行着业务的容器中&am…

Python 2025:低代码开发与自动化运维的新纪元

从智能运维到无代码应用&#xff0c;Python正在重新定义企业级应用开发范式在2025年的企业技术栈中&#xff0c;Python已经从一个"开发工具"演变为业务自动化的核心平台。根据Gartner 2025年度报告&#xff0c;68%的企业在自动化项目中使用Python作为主要开发语言&am…

Netty 在 API 网关中的应用篇(请求转发、限流、路由、负载均衡)

Netty 在 API 网关中的应用篇&#xff08;请求转发、限流、路由、负载均衡&#xff09;随着微服务架构的普及&#xff0c;API 网关成为服务之间通信和安全控制的核心组件。在构建高性能网关时&#xff0c;Netty 因其高吞吐、低延迟和异步非阻塞 IO 的特性&#xff0c;成为不少开…

基于STM32设计的青少年学习监控系统(华为云IOT)_282

文章目录 一、前言 1.1 项目介绍 【1】项目开发背景 【2】设计实现的功能 【3】项目硬件模块组成 【4】设计意义 【5】国内外研究现状 【6】摘要 1.2 设计思路 1.3 系统功能总结 1.4 开发工具的选择 【1】设备端开发 【2】上位机开发 1.5 参考文献 1.6 系统框架图 1.7 系统原理…

手写Spring底层机制的实现【初始化IOC容器+依赖注入+BeanPostProcesson机制+AOP】

摘要&#xff1a;建议先看“JAVA----Spring的AOP和动态代理”这个文章&#xff0c;解释都在代码中&#xff01;一&#xff1a;提出问题依赖注入1.单例beans.xml<?xml version"1.0" encoding"UTF-8"?> <beans xmlns"http://www.springframe…

5G NR-NTN协议学习系列:NR-NTN介绍(2)

NTN网络作为依赖卫星的通信方式&#xff0c;需要面对的通信距离&#xff0c;通信双方的移动速度都和之前TN网络存在巨大差异。在距离方面相比蜂窝地面网络Terrestrial Network通信距离从最小几百米到最大几十km的情况&#xff0c;NTN非地面网络的通信距离即使是近地轨道的LEO卫…

线扫相机采集图像起始位置不正确原因总结

1、帧触发开始时间问题 问题描述: 由于帧触发决定了线扫相机的开始采集图像位置,比如正确的位置是A点开始采集,结果你从B点开始触发帧信号,这样出来的图像起始位置就不对 解决手段: 软件需要记录帧触发时轴的位置 1)控制卡控制轴 一般使用位置比较触发,我们可以通过监…

校园管理系统练习项目源码-前后端分离-【node版】

今天给大家分享一个校园管理系统&#xff0c;前后端分离项目。这是最近在练习前端编程&#xff0c;结合 node 写的一个完整的项目。 使用的技术&#xff1a; Node.js&#xff1a;版本要求16.20以上。 后端框架&#xff1a;Express框架。 数据库&#xff1a; MySQL 8.0。 Vue2&a…

【项目】 :C++ - 仿mudou库one thread one loop式并发服务器实现(模块划分)

【项目】 &#xff1a;C - 仿mudou库one thread one loop式并发服务器实现一、HTTP 服务器与 Reactor 模型1.1、HTTP 服务器概念实现步骤难点1.2、Reactor 模型概念分类1. 单 Reactor 单线程2. 单 Reactor 多线程3. 多 Reactor 多线程目标定位总结二、功能模块划分2.1、SERVER …

浴室柜市占率第一,九牧重构数智卫浴新生态

作者 | 曾响铃文 | 响铃说2025年上半年&#xff0c;家居市场在政策的推动下展现出独特的发展态势。国家出台的一系列鼓励家居消费的政策&#xff0c;如“以旧换新”国补政策带动超6000万件厨卫产品焕新&#xff0c;以及我国超2.7亿套房龄超20年的住宅进入改造周期&#xff0c;都…