JVM系列(7)——java内存模型

news2024/11/24 22:49:39

一、什么是JMM

一种抽象的规范。每个JVM 的实现都要遵守这样的规范,这样才能保证Java程序能够“一次编写,到处运行”。
内存模型描述了程序中各个变量(实例域、静态域和数组元素)之间的关系,以及在实际计算机系统中将变量存储到内存和从内存中取出这样的底层细节。

二、JMM结构

1、CPU缓存模型

直接上图:
在这里插入图片描述
《深入理解高并发编程》 6.1.2 章节CPU多级缓存架构原理。
ps:挡住的字是,计算机中的主内存是所有cpu都可以访问的,并且主内存的容量比cpu缓存大。
在这里插入图片描述
图片来源:https://github.com/Snailclimb/JavaGuide/issues/1848
解释一下:
计算机在执行程序时,每条指令都是在CPU中执行的。而执行指令的过程中,势必涉及到数据的读取和写入。
程序运行过程中的临时数据是存放在主存(物理内存)当中的,这个时候,在读取写入数据时,CPU处理速度是远远大于内存的处理速度的!两个完全不一致。
CPU缓存模型的工作方式: 先复制一份数据到 CPU Cache 中,当 CPU 需要用到的时候就可以直接从 CPU Cache 中读取数据,当运算完成后,再将运算得到的数据写回 Main Memory 中。但是,依然会存在内存缓存数据不一致问题,这时候,通过制定缓存一致协议(比如 MESI 协议)可以解决此问题。

2、JMM模型

在这里插入图片描述
图片来源我的另一篇博客:多线程与高并发(2)——synchronized用法详解
解释一下:
从抽象的角度来看,JMM定义了线程和主内存之间的抽象关系:线程之间的共享变量存储在主内存(main memory)中,每个线程都有一个私有的本地内存(local memory),本地内存中存储了该线程以读/写共享变量的副本。本地内存是JMM的一个抽象概念,并不真实存在。
主内存:所有线程创建的实例对象都存放在主内存中,不管该实例对象是成员变量还是方法中的本地变量(也称局部变量)
本地内存:每个线程都有一个私有的本地内存来存储共享变量的副本,并且,每个线程只能访问自己的本地内存,无法访问其他线程的本地内存。本地内存是 JMM 抽象出来的一个概念,存储了主内存中的共享变量副本。
比如X=0,线程1改成了X=1,那么它要同步给主内存,主内存再给到线程2,这就是线程之间的可见性
而,关于JMM的三大特性:原子性、可见性、有序性,可以参考多线程与高并发(2)——synchronized用法详解。

三、乱序执行&&禁止乱序

以下内容均可参考:
多线程与高并发(2)——synchronized用法详解。
多线程与高并发(5)——volatile关键字详解
多线程与高并发(3)——synchronized原理

1、乱序执行

cpu为了提高执行效率,当a指令去做其他事时,让b指令来执行。
不得不提的是,指令重排序。变量赋值操作的顺序与程序代码中的执行顺序是不一致的。
而为了防止乱序执行,JVM级别怎么规范呢?
类似于CPU内存屏障那样,JVM也定义了内存屏障。
在这里插入图片描述

2、volatile禁止乱序实现细节

(1)字节码层面
ACC_VOLATILE标识符。
(2)JVM层面
写的时候,前面加SS指令,后面加SL指令;
读的时候,前面加LL指令,后面加LS指令。
(3)OS和硬件层面
lock指令。

3、synchronized禁止乱序实现细节

(1)字节码层面
ACC_SYNCHRONIZED标识符,monitorenter和monitorexit标识符。
(2)JVM层面
c/c++调用操作系统提供的同步机制。
(3)OS和硬件层面
lock指令。

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

华为产品测评官-开发者之声 - ModelArts 真实体验感想

华为产品测评官-开发者之声 - ModelArts 真实体验感想 我先是在6月17日参加了华为在深圳举办的开发者大会,后面看到群里发的"2023华为产品测评官-开发者之声"活动,简单看了一下体验活动的具体事情,感觉好玩…

mysql 第六章

目录 1.子查询 2.exists 3.as 别名 4.视图 5.null 6.连接查询 7.总结 1.子查询 2.exists 3.as 别名 4.视图 5.null 6.连接查询 7.总结 对 mysql 数据库的查询,除了基本的查询外,有时候需要对查询的结果集进行处理。

【Policy】使用 InitializingBean 实现策略时如何避免AOP失效

使用InitializingBean实现策略模式 参考策略模式示例中的第一种实现方式.代码demo项目 不同的注入方式对AOP注解的影响 部分策略代码及测试代码 public interface TraditionOrderService extends InitializingBean {// ... } Service public class TraditionOrderServiceIm…

原生信息流广告APP应用内增收及计费模式

比起传统的广告宣传,信息流最大的优势就在于流量的庞大。与此同时,多样化的信息流广告形式和精准的定向,还可以帮助广告主准确获取意向流量。此外,它的广告形式不强迫推送,因此也受到了广泛用户的支持和青睐。 原生信…

Java:输入与输出

目录 输入输出args 输入Scanner 输入格式化输出文件输入与输出 输入输出 args 输入 利用main函数中的参数args,当然也可以起别的名字。其他语言也是一样的。输入时空格分隔。 args的作用:在程序启动时可以用来指定外部参数 Scanner 输入 需要import j…

26.JavaWeb-SpringSecurity安全框架

1.SpringSecurity安全框架 Spring Security是一个功能强大且灵活的安全框架,它专注于为Java应用程序提供身份验证(Authentication)、授权(Authorization)和其他安全功能。Spring Security可以轻松地集成到Spring框架中…

Docker高级——网络配置

Docker网络 默认网络 安装 Docker 以后,会默认创建三种网络,可以通过 docker network ls 查看 [roottest ~]# docker network ls NETWORK ID NAME DRIVER SCOPE 6f24f7cbfa10 bridge bridge local 2dc34a1c0f04 host host…

微信号长期没有使用或被回收?

7月17日,有网友表示自己之前申请了一个辅助账号作为树洞使用,如今登录的时候,弹出文字提示称“该微信号由于长期没有使用已被回收”。 腾讯客服回应表示,正常登录使用的微信号不会被系统回收,但对于长时间未登录的微信…

简用前后端的JSON格式注解:@DateTimeFormat、@JsonFormat、@JsonProperty

JsonFormat 【后端到前端】 在实体类属性上面使用JsonFormat注解了,要注意的是,它只会在声明返回类型为json时,比如使用ResponseBody返回json数据的时候,才会返回格式化的yyyy-MM-dd HH:mm:ss时间,如果直接使用Syste…

【分布式系统案例课】查询服务设计、计数栈选型、总结

查询服务设计 数据获取路径 两个问题考虑: 1、老数据归档的问题。 如果所有分钟小时级的数据一直存在这个DB当中,那么DB的存储空间会被不断的消耗,性能也会不断的下降。所以一旦小时天月的数据聚合完成,我们就可以将一些老的原始…

java: 错误: 不支持发行版本 5 java: 错误: 不支持发行版本8 java: 错误: 不支持发行版本17

🍓🍓原因 该错误表示你使用的Java编译器不支持Java 5版本的发行。Java版本的发行是根据不同的功能和语言变化来区分的。 要解决这个问题,你可以尝试以下几种方法: 检查编译器配置:确保你的IDE或编译器已正确配置为使…

Segment Tree 线段树算法(java)

线段树算法 Segment Tree 线段树算法代码演示 蓄水池算法 Segment Tree 线段树算法 什么是线段树算法: 线段树(Segment Tree)是一种基于树结构的数据结构,用于解决区间查询问题,例如区间最大值、最小值、区间和等。线段…

【数据结构】图解八大排序(下)

文章目录 一、前言二、快速排序1. hoare 版2. 挖坑法3. 前后指针法4. 快排的非递归实现5. 时空复杂度分析 三、归并排序1. 递归实现2. 非递归实现 四、计数排序 一、前言 在上一篇文章中,我们已经学习了五种排序算法,还没看过的小伙伴可以去看一下&…

C语言 —— 浮点类型详解及 IEEE754 规定

【C语言趣味教程】(3) 浮点类型:单精度浮点数 | 双精度浮点型 | IEEE754 标准 🔗 《C语言趣味教程》👈 猛戳订阅!!! ​—— 热门专栏《维生素C语言》的重制版 —— 💭 写在前面:这是…

Paragon NTFS2023中文最新版mac读写NTFS移动硬盘

当我们使用macOS系统将数据拷贝或写入NTFS格式磁盘时,却发现不能操作成功。搜索原因或解决方案时,许多网友推荐安装磁盘管理软件——Paragon NTFS for Mac。 往往大家都会有两个疑问,一是为什么非要使用NTFS格式的磁盘?二是为什么…

C/C++程序内存区域划分以及各区域的介绍

C/C程序内存区域划分 直接上图: 在这里插入图片描述 注:以下的说明均已VS2019为例 栈区(stack) 在执行函数时,函数内局部变量的存储单元都可以在栈上创建,函数执行结束时这些存储单元会自动释放。栈内…

用自己的数据拟合Sigmoid函数(Matlab平台)

%% 拟合sigmoid曲线 sigmoid (params, x) params(1) ./ (1 exp(-params(2) .* (x - params(3)))) params(4); %params(1) 是斜率参数,params(2) 是增长速率参数,params(3) 是 x 值的偏移参数,params(4) 是 y 值的偏移参数。 initialGuess…

剑指offer刷题笔记--Num51-60

1--数组中的逆序对&#xff08;51&#xff09; 主要思路&#xff1a; 基于归并排序&#xff0c;视频讲解参考&#xff1a;数组中的逆序对 #include <iostream> #include <vector>class Solution { public:int reversePairs(std::vector<int>& nums) {if(…

【力扣算法17】之 19. 删除链表的倒数第 N 个结点 python

文章目录 问题描述示例1示例2示例3提示 思路分析代码分析完整代码详细分析运行效果截图完结 问题描述 给你一个链表&#xff0c;删除链表的倒数第 n 个结点&#xff0c;并且返回链表的头结点。 示例1 输入&#xff1a;head [1,2,3,4,5], n 2 输出&#xff1a;[1,2,3,5] 示例2…

加强安全防护,提升日志管理——探索EventLog Analyzer

导言&#xff1a; 在当今数字化时代&#xff0c;安全威胁和数据泄露已经成为各个组织和企业面临的严峻挑战。有效的日志管理和监控是确保网络安全的重要一环。本文将介绍EventLog Analyzer&#xff08;事件日志分析器&#xff09;这一强大工具&#xff0c;探索其在日志安全方面…