Java对象结构与内置锁

news2024/10/6 20:25:47

Java对象结构与内置锁

Java内置锁的很多重要信息都存放在对象结构中

1.Java对象结构

Java对象包括三部分:对象头、实例数据和对齐字节
在这里插入图片描述

  • 对象头:

    • 第一个字段叫做Mark Word,用于存储自身运行时数据,例如GC标志位,哈希码,锁状态信息
    • 第二个字段叫做Class Pointer(类对象指针),用于存放方法区Class对象的地址,虚拟机通过这个指针来确定这个对象属于哪个类的实例
    • 第三个字段叫做Array Length(数组长度)。如果队形是一个Java数组,那么此字段必须要有,用于记录数组长度的数据;如果对象不是一个数组,那么此字段不存在,所以这是一个可选字段
  • 实例数据

    ​ 实例数据存放的就是对象的实例数据,用于成员属性值,包括父类的成员属性值。

  • 对齐填充

​ 没有作用,只是为了填充长度

2.对象结构中核心字段的运用

  • Mark Word字段主要用来表示对象的线程锁状态,另外可以用来配合GC存放该对象的hashCode
  • Class Pointer字段是一个指向方法区的Class信息指针,意味着该对象随时可以知道自己是哪个对象的实例
  • Array Length字段占用32位,这是可选的,只有当本对象是一个数组对象时才会有这个部分
  • 对象体用于保存对象的属性值,是对象的主题部分,占用的内存空间大小取决于对象的属性数量和类型
  • 对齐字节并不是必然存在的

3.对象结构中字段的长度

​ Java内置锁的状态共有四级:无锁、偏向锁、轻量级锁、重量级锁。在jdk1.6之前Java的内置锁只有一个重量级锁,但是在1.6之后,JVM为了提高锁的获取和释放效率,对synchronized的实现进行了优化,引入了偏向锁和轻量级锁,从此Java的内置锁就有了4种状态,并且会随着竞争的情况逐渐升级,而且是不可逆的过程,即不会降级,也就是说只能升级。

​ Mark Word字段的结构与Java内置锁的状态相关。为了让Mark Word字段存储更多的信息,JVM将Mark Word最低的两个位设置为Java的内置锁状态位,不同的锁状态下的32位Mark Word结构也不同
在这里插入图片描述

64位Mark Word的构成
  • lock: 锁状态标记,占两个二进制位,由于希望用尽可能少的二进制位表示尽可能多的信息,因此设置了lock标记。该标记的值不同,整个Mark Word表示的含义就不同
  • biased_lock :对象是否为偏向锁标记,只占一个二进制位。为1时表示对象启用偏向锁,为0时表示对象没有启用偏向锁

​ lock和biased_lock两个标记位组合在一起共同表示Object实例处于什么样的锁状态

  • age: 4位的Java对象分代年龄。
  • identity_hashcode:31位的对象标识hashCode,采用延时加载技术,当调用Object.hashCode方法或者System.identityHashCode()方法计算对象的HashCode后,其结果将被写入到该对象的头中。当对象被锁定的时候,该值会移动到Moniteor中
  • thread: 54位的线程Id
  • epoch: 偏向时间戳
  • ptr_to_lock_record: 62位,轻量级锁状态下指向栈帧中锁记录的指针
  • ptr_to_heavyweight_monitor:62位,在重量级锁的状态下指向对象监视器的指针

4.无锁、偏向锁、轻量级锁、重量级锁

​ 在jdk1.6版本之前,所有的Java内置锁都是重量级锁,重量级锁会造成CPU在用户态和核心态之间频繁切换,所以代价高、效率低。jdk1.6版本为了减少获得锁和释放锁所带来的性能消耗,引入了偏向锁和轻量级锁的实现。

  • 无锁状态

    Java对象刚创建的时候还没有任何线程来竞争,说明该对象时处于无锁状态,这时候偏向锁标识位是0,锁状态是01,无锁状态下的Mark Word如图所示:

  • 偏向锁状态

    ​ 偏向锁是指一段同步代码一直被同一个线程所访问,那么该线程会自动获取锁,降低获取锁的代价。如果内置锁处于偏向状态,当有一个线程来竞争锁的时候,先用偏向锁,标识内置锁偏爱这个线程,这个线程要执行该锁关联的同步代码时,不需要再做任何检查和切换。偏向锁在竞争不激烈的情况下效率非常高

    ​ 偏向锁状态的Mark Word会记录内置锁自己偏爱的线程id,内置锁会将该线程当作自己熟悉的人

在这里插入图片描述

  • 轻量级锁

​ 当有两个线程开始竞争这个锁对象的时候,情况就发生了变化,不在是偏向哪个线程了,锁会升级为轻量级锁,两个锁公平竞争,哪个线程先占有锁对象,锁对对象的Mark Word就只想哪个线程栈帧中的锁记录。

在这里插入图片描述

​ 当锁处于偏向锁,又被另一个线程企图抢占时,偏向锁就会升级成轻量级锁,企图强占的线程就会通过自旋的形式尝试获取锁,不会阻塞抢占线程,以便提高性能。

​ 自旋的原理十分简单,如果持有锁的进程能在很短时间内释放锁资源,那么那些等待竞争锁的线程就不需要在内核态和用户态之间切换线程来进入阻塞状态,他们只需要等一等(自旋),等持有锁的线程释放掉锁后即可立即获取锁,这样就避免了用户线程和内核切换的消耗。

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

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

相关文章

P1120 小木棍(搜索+剪枝)

题目链接:P1120 小木棍 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn) 样例输入: 9 5 2 1 5 2 1 5 2 1 样例输出: 6 分析:这道题一看数据范围就知道是搜索,但关键是需要剪枝。 首先我们求出所有木棍的长度和&am…

什么是刺猬理念

一、什么是刺猬理念刺猬理念是指把复杂的世界简化成单个有组织性的观点,一条基本原则或一个基本理念,发挥统帅和指导作用。核心是把事情简单化,把所有的挑战和进退维谷的局面压缩为简单的。二、刺猬理念的寓言故事狐狸是一种狡猾的动物&#…

Maix Bit(K210)保姆级入门上手教程---自训练模型之云端训练

Maix Bit(K210)保姆级入门上手教程系列 Maix Bit(K210)保姆级入门上手教程—环境搭建 Maix Bit(K210)保姆级入门上手教程—外设基本使用 这是K210快速上手系列文章,主要内容是,介绍…

《机器学习》基础概念之【P问题】与【NP问题】

《机器学习》基础概念之【P问题】与【NP问题】 这里写目录标题《机器学习》基础概念之【P问题】与【NP问题】一、多项式&时间复杂度1.1. 多项式1.2.时间复杂度二、P问题 & NP问题2.1. P问题2.2.NP问题2.3.举例理解NP问题-TSP旅行商推销问题三、NP-hard问题&NP-C问题…

PMP项目管理项目成本管理

目录1 项目成本管理概述2 规划成本管理3 估算成本4 制定预算5 控制成本1 项目成本管理概述 项目成本管理包括为使项目在批准的预算内完成而对成本进行规划、估算、预测、融资、筹资、管理和控制的各个过程,从而确保项目在批准的预算内完工。核心概念 项目成本管理旨…

vuex getters的作用和使用(求平均年龄),以及辅助函数mapGetters

getters作用:派生状态数据mapGetters作用:映射getters中的数据使用:方法名自定义,系统自动注入参数:state,每一个方法中必须有return,其return的结果被该方法名所接收。在state中声明数据listst…

PyTorch深度学习实战 | 计算机视觉

深度学习领域技术的飞速发展,给人们的生活带来了很大改变。例如,智能语音助手能够与人类无障碍地沟通,甚至在视频通话时可以提供实时翻译;将手机摄像头聚焦在某个物体上,该物体的相关信息就会被迅速地反馈给使用者&…

【教学典型案例】21.面向对象复用、面向对象实现、立体化权限落地

目录一:背景介绍1、针对于激励配置的功能体现出来的:面向对象的思想就可以实现极大程度的复用性的问题2、脱离学习通设计图,过程化,如何用面向对象的思想来去组织管理流程图3、词云位置记录定制化二:思路&方案1、面…

CSDN每日一练(编程题)

目录1. 2023/1/31-非降序数组(类型:数组&排序 难度:中等)2. 2023/2/1- 走楼梯(类型:递归&循环 难度:中等)3. 2023/2/1-蛇形矩阵(难度:困难)4. 2023/2/2-奇偶排序(类型:数组&奇偶排序 难度&…

环境配置之Keepass

前言很久以前,就有了想要一个自己密码管理器的念头。毕竟,即使浏览器能记住各个网站的账号密码,但是在登录单独客户端的时候,仍然要翻找密码。为了省事,也曾经是一个密码走天下。然后被劫持了QQ给同学发黄色小网站&…

手写Mybatis

Mybatis总体流程 (1)加载配置并初始化触发条件:加载配置文件 配置来源于两个地方,一个是配置文件(主配置文件conf. xml, mapper文件*.xml),一个是java代码中的注解,将主配置文件内容解析封装到Configuration,将sql的配置信息加载成为一个mappedstateme…

ReentrantLock源码分析(一)加锁流程分析

一、ReetrantLock的使用示例 static ReentrantLock lock new ReentrantLock(); public static void main(String[] args) throws InterruptedException { new Thread(ClassLayOutTest::reentrantLockDemo, "threadA").start(); Thread.sleep(1000);…

Netty权威指南总结(二)

三、Netty代码相关:(四) EventLoop与EventLoopGroup:Netty的Nio线程是NioEventLoop。1. Reactor线程模型:Reactor模型的三个角色:Reactor:把IO事件分配给对应的Handler处理,功能像是调度器。Acceptor【饿渴…

【C++】C++核心编程(一)---内存四区

C程序在执行时,将内存大方向划分为4个区域 代码区 存放函数体的二进制代码,由操作系统进行管理全局区 存放全局变量和静态变量以及常量(字符串常量、全局常量)栈区 由编译器自动分配释放,存放函数的参数值、局部变量等堆区 由程序员分配和释…

jenkins问题

目录 python 不是内部或外部命令,也不是可运行的程序 ‘cmd’ 不是内部或外部命令,也不是可运行的程序或批处理文件。 git 不是内部或外部命令,也不是可运行的程序或批处理文件。 pywintypes.com_error: (-2147024891, ‘拒绝访问。’, None,…

Qt实用技巧:Qt中浮点数的相等比较方式(包括单精度和双精度)

若该文为原创文章,转载请注明原文出处 本文章博客地址:https://hpzwl.blog.csdn.net/article/details/129464152 红胖子(红模仿)的博文大全:开发技术集合(包含Qt实用技术、树莓派、三维、OpenCV、OpenGL、ffmpeg、OSG、单片机、软…

Spring——AOP切入点表达式和AOP通知类型

切入点:要进行增强的方法 切入点表达式:要进行增强的方法的描述式 第一种方法的本质是基于接口实现的动态代理(jdk) 第二种是基于cglib实现的动态代理 AOP切入点表达式 而需要加载多个切入点时,不可能每个切入点都写一个切入点表达式 例子 下面的代理描述的是匹配…

条件语句(分支语句)——“Python”

各位CSDN的uu们你们好呀,最近总是感觉特别特别忙,但是却又不知道到底干了些什么,好像啥也没有做,还忙得莫名其妙,言归正传,今天,小雅兰的内容还是Python呀,介绍一些顺序结构的知识点…

Hadoop学习:Yarn

1.YARN介绍 一个通用的资源管理系统和调度平台 YARN不分配磁盘,由HDFS分配 相当于一个分布式的操作系统平台,为上层MR等计算程序提供运算所需要的资源(内存、CPU等) 2.YARN三大组件 不要忘记AppMaster,他是程序内部…

Android 进程间通信机制(二) mmap 原理

一. 前言 Binder中一次拷贝的实现就是利用mmap(memory mapping)内存映射机制,我们来看看它的工作原理. 二. 参考文章 下面这几篇文章建议先好好阅读一下,都是总结的很好的文章, 每个人理解可能不一样 笔者也是看了好多博客文章和B站视频讲解, 然后加上自己的理解后 输出的一…