synchronized锁详解

news2024/11/26 8:56:33

本文主要是对synchronized使用各个情况,加解锁底层原理的讲解

一,重量级锁

对象头

讲重量级锁之前,先了解一下一个对象的构成,一个对象是由对象头和对象体组成的,本文主要讲对象头,对象体其实就是对象的成员变量,对象头由mark word 和klass word组成,klass word就是指当前对象的类型,而mark word在正常状态下就是指对象的hashcode,所处的年代,是否是偏向锁,加锁的状态,见下图

monitor(锁)--操作系统底层实现,不由我们直接控制

接下来正式进入重量级锁的讲解,首先每一个java对象都可以关联一个monitor对象,只要我们使用synchronized,就会将该对象的markwork设置为改monitor的指针地址,并设置状态为10,见上图的第四行

 整个步骤为:

  1. 首先一开始monitor对象没有和任何对象做绑定,当第一次执行synchronized代码块时,就会将其对象与底层的monitor对象做绑定,将monitor对象的指针地址替换掉对象本身的markword
  2. 设置monitor对象的owner为当前线程的栈帧
  3. 当有第二个线程进入synchronized代码块时,首先判断当前对象的markword有没有指向monitor,没有的话,则执行前两步骤,否则去判断owner是否指向某个线程,是的话,则进入monitor的entrylist进入阻塞,等待owner执行完毕,不是的话,则执行1,2步骤
  4. 释放锁时,首先找到当前对象的引用地址,然后获取markword中的monitor对象地址,然后从monitor中清除掉owner指向的当前线程,然后从monitor中拿到对象正常状态下的markword进行重置,还原正常状态,然后唤醒entrylist中的所有线程,抢占时间按片重复上述步骤即可
  5. 当synchronized代码块出现异常也不用担心,同样会帮我们重置当前对象的状态,并唤醒entrylist中的线程,然后会抛出异常,避免死锁

二,轻量级锁

轻量级锁并不是用来替换重量级锁的,我们知道,monitor是操作系统提供给我们的对象,频繁的操作它加解锁实际上是一个很消耗性能的操作,当我们线程竞争没那么频繁的时候,比如我前一个线程执行完代码块,后一个线程才进入,那么我就没必要加锁,当竞争频繁的时候我们再升级为重量级锁

具体步骤如下:

  1. 首先当执行到 synchronized代码块时,会在当前线程栈中写入一个锁记录lock record,然后将当前对象的引用地址写入锁记录的object reference中
  2. 将当前对象的markword和锁记录的地址通过cas进行交换,状态切换为00就是轻量级锁,见图一的第三行,如果当前对象的状态为01则可以交换成功,表示当前对象由当前线程持有,如果为00则会交换失败,说明但前锁已经被别人持有了,这个时候又会分为两种情 况:
  • 第一线程重入,就是说持有锁的是当前线程,那么因为又执行了synchronized代码块,左边的栈中又写入一条栈帧锁记录   ,但是因为替换失败所以锁记录的地址为null,当前线程锁次数加一,因为本身是当前线程获取到了锁,所以仍然可以进入代码块执行,当执行完里层的synchronized代码块,就会将当前线程锁的次数减一,当执行到最外层的代码块时判断如果锁记录有值说明是最后一层,并判断当前线程锁的次数,如果为0则释放锁;
  •   第二种就是,之气获取到锁的不是当前线程,那么锁就会升级为重量锁(或者专业点说叫锁膨胀),并把对象的markword由锁记录地址替换为monitor对象的地址,并将monitor的owner指向之前线程的栈地址,将当前线程放入entrylist阻塞等待

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

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

相关文章

核心实验21_BGP高级(了解)(配置略)_ENSP

项目场景: 核心实验21_BGP基础_ENSP 通过bgp实现省市互通。 实搭拓扑图: 具体操作: 其他基础配置略(接口地址,ospf) 1.BGP邻居建立: R1: [R1]bgp 200 [R1-bgp]peer 10.2.2.2 as-number 200 …

Java高级之File类、节点流、缓冲流、转换流、标准I/O流、打印流、数据流

第13章 IO流 文章目录 一、File类的使用1.1、如何创建File类的实例1.2、常用方法1.2.1、File类的获取功能1.2.2、File类的重命名功能1.2.3、File类的判断功能1.2.4、File类的创建功能1.2.5、File类的删除功能 二、IO流原理及流的分类2.1、Java IO原理2.2、流的分类/体系结构 三…

LINUX内核启动流程-2

向32位模式转变,为main函数的调用做准备 1、关中断并将system移动到内存地址起始位置0x00000 1.1 关中断:将CPU的标志寄存器(EFLAGS)中的中断允许标志(IF)置0。 main函数中能够适应保护模式的中断服务体系被重建完毕才会打开中断,而那时候响应中断的服务程序将不再是…

【数据结构与算法】不就是数据结构

前言 嗨喽小伙伴们你们好呀,好久不见了,我已经好久没更新博文了!之前因为实习没有时间去写博文,现在已经回归校园了。我看了本学期的课程中有数据结构这门课程(这么课程特别重要),因为之前学过一点&#xf…

天宇微纳芯片测试软件如何测试电源芯片的持续电流?

持续电流(连续电流)是指元器件在工作状态下内部电流持续流动的状态,一般都是用于对元器件允许连续通过电流限制的一种描述。比如电源芯片允许的持续电流,就表示该芯片可连续通过的最大电流。 通过上面的描述我们可以知道&#xff…

爬虫 — 验证码反爬

目录 一、超级鹰二、图片验证模拟登录1、页面分析1.1、模拟用户正常登录流程1.2、识别图片里面的文字 2、代码实现 三、滑块模拟登录1、页面分析2、代码实现(通过对比像素获取缺口位置) 四、openCV1、简介2、代码3、案例 五、selenium 反爬六、百度智能云…

zabbix学习1--zabbix6.x单机

文章目录 1. 环境2. MYSQL8.02.1 单节点2.2 配置主从 3. 依赖组件4. zabbix-server5. agent5.1 yum5.2 编译 附录my.cnfJDK默认端口号 1. 环境 进入官网查看所需部署环境配置以及应用版本要求https://www.zabbix.com/documentation/current/zh/manual/installation/requiremen…

机器学习(11)---降维PCA

目录 一、概述1.1 维度1.2 sklearn中的降维算法 二、降维实现原理2.1 PCA与SVD2.2 降维实现2.3 降维过程 三、鸢尾花数据集降维3.1 高维数据的可视化3.2 探索降维后的数据3.3 累积可解释方差贡献率曲线 四、选n_components参数方法4.1 最大似然估计自选超参数4.2 按信息量占比选…

期权开户流程、交易时间和规则详解清晰易懂

本文将介绍期权开户流程、交易时间和规则详解清晰易懂则,包括期权的定义、期权交易的时间、期权交易的规则和期权交易的风险。本文的结论是,期权交易的时间和规则非常重要,应该遵守交易规则,并且要注意风险。本文来源:…

VB求组合数

VB求组合数 求组合数C(m,n)n!/(m!(n-m)!) m6,n10 Private Function fact(x As Integer) As LongDim i As Integer, f As Longf 1For i 1 To xf f * iNext ifact f End Function Private Sub Command1_Click()Dim m%, n%, u As Long, v As Long, w As Longm 6: n 10u fa…

Maven的介绍和使用

Maven的作用 项目构建 依赖管理:避免资源间版本冲突问题 统一开发结构:提供统一的项目结构 Maven的使用 下载完压缩包之后放在合适的目录下,其中apache-maven-3.8.8文件夹是安装的maven,下面的repository是本地仓库&#xff…

手写一个springboot starter,并使用starter

文章目录 前言一、starter的作用和意义二、自定义一个starter并使用1.starter本体问题: 2.创建另外一个项目,引入自定义的starter 总结spring-configuration-metadata.json 前言 你一定用过很多starter , 例如 spring-boot-starter,spring-boot-starter-test等等,那么如何实现…

微信群发超过5000人是怎么办到的?

你是否好奇,微信官方对于普通用户的群发限制是500人,但是有些大佬的微信账号怎么能群发突破这个限制,甚至超过5000人,其实他们有可能都用到了这一款软件: https://youwokeji.feishu.cn/docx/RpybdOWpzo9tlqxlMk7c0VZb…

从键盘任意输出一个整数n,若n不是素数,则计算并输出其所有因子(不包括1),否则输出该数为素数

#include<stdio.h> int main() {int i 0;int j 0;int n 0;int tag 0;//设置一个标志位&#xff0c;不为素数时令tag1&#xff1b;printf("输入一个数&#xff1a;");scanf("%d", &n);for (i 2; i < n; i){if (n % i 0){printf("该…

让小爱同学播放本地/远程歌曲的方案 | 小爱音箱播放本地歌曲

环境:HACS+Python 问题:小爱同学不能播放本地歌曲或者群晖中的歌曲 解决办法:HACS + Http Server 背景:冲绿砖是不可能的,DLNA也被阉割了,只能曲线救国了 解决思路:通过HACS监控小爱事件,推送媒体链接并随机播放,具体看下面的流程图 文章目录 1.安装HACS:2.安装HACS…

操作系统的体系结构

一、内核结构 操作系统内核也有两种类别&#xff1a;大内核结构、微内核结构 大内核结构&#xff1a;也叫宏内核/单内核。将操作系统的主要功能模块都作为操作系统内核。大内核结构包括进程管理、存储器管理、设备管理等功能&#xff08;第四层&#xff09;和时钟管理、中断处理…

SpringSecurity 初始化解析

文章目录 前言加载SpringSecurity配置解析配置SpringSecurity 解析器security:http 解析FilterChainProxy的注册过程创建 SpringSecurity 过滤器总结 前言 通过上文分析知道了SpringSecurity对一个请求的具体处理流程。不知道大家是否跟我一样都有几个疑问&#xff1a; Filte…

半导体行业如何在跨网数据交换时保证核心数据是安全的?

半导体行业是高科技产业的核心&#xff0c;也是国家战略的重点领域。半导体产业涉及到芯片设计、制造、封装、测试等多个环节&#xff0c;每个环节都需要大量的数据支撑和交换。半导体企业的核心数据不仅包括技术方案、设计图纸、生产参数等&#xff0c;还包括市场分析、客户信…

创建当前工作簿的备份和一次关闭所有工作簿

【分享成果&#xff0c;随喜正能量】专注地做一件事&#xff0c;做到极致&#xff0c;胜过敷衍地做很多事。不求多&#xff0c;但求精&#xff0c;不求散&#xff0c;但求专。每个人的时间和精力都是有限的&#xff0c;专注于某个领域&#xff0c;沉得住气&#xff0c;静得下心…