没有合适的资源?快使用搜索试试~ 我知道了~
资源推荐
资源详情
资源评论
Java 多线程
Synchronized
1.1 synchronized 简述
synchronized 被称为重量级锁 , 但是 1.6 版本后得到了优化 , 相对
轻量了很多, 它可以保证在同一个时刻,只有一个线程可以执行某个方
法或者某个代码块 .
主要操作对象是方法或者代码块中存在的共享数据, 同时可保证一个线
程的变化(主要是共享数据的变化)被其他线程所看
synchronized 的核心原理为 Java 对象头 以及 Monitor
JVM 基于进入和退出 Monitor 对象来实现方法同步和代码块同步
1.2 Java 对象头 和 Monitor
对象头结构
// 原理 -->
1 Java 对象头 和 Monitor
|-> 对象头 :
|-> Mark Word(标记字段)、Klass Pointer(类型指针)
|-> Klass Pointer : 类元数据指针,决定是何数据
|-> Mark Word : 自身运行时数据 (hashcode,锁状态,偏向,标
志位等)
|-> Monitor :
|-> 互斥 :一个 Monitor 锁在同一时刻只能被一个线程占用
// 关系 -->
- Monitor 是一种对象类型 , 任何 Java 对象都可以是 Monitor 对象
- 当 Java 对象被 synchronized 修饰时 , 就可以当成 Monitor 对象
进行处理
// Mark Word 和 Class Metadata Address 组成结构
----------------------------------------------------------------------------
----------------------
虚拟机位数 头对象结构 说明
|---------|-----------------------|-------------------------------------------
--------------------|
32/64bit Mark Word 存储对象的 hashCode、锁信息
或分代年龄或 GC 标志等信息
32/64bit Class Metadata Address 类型指针指向对象的类元数据,
JVM 通过这个指针确定该对象是哪个类的实例。
----------------------------------------------------------------------------
----------------------
32 位虚拟机 Mark Word >>>>
64 位虚拟机 Mark Word >>>>
数据结构
// Monitor 的 实 现 方 式 @
https://blog.csdn.net/javazejian/article/details/70768369
ObjectMonitor 中有两个队列以及一个区域
_WaitSet 和 _EntryList,用来保存 ObjectWaiter 对象列表( 每个
等待锁的线程都会被封装成 ObjectWaiter 对象)
_owner (指向持有 ObjectMonitor 对象的线程) 区域
1 当多个线程同时访问一段同步代码时,首先会进入 _EntryList 集合,
此时开始尝试获取 monitor
2 当 线 程 获 取 到 对 象 的 monitor 后 进 入 _Owner 区 域 , 并 把
monitor 中的 owner 变量 设置为当前线程同时 monitor 中的计数器
count 加 1
3 若线程调用 wait() 方法,将释放当前持有的 monitor,owner 变量
恢复为 null,count 自减 1,同时该线程进入 WaitSet 集合中等待被唤
醒。
4 若当前线程执行完毕 也将 释放 monitor(锁) 并 复位变量的值,以
便 其他线程进入获取 monitor(锁)
Monitor 指令
monitorenter 指令是在编译后插入到同步 代码块的开 始位置,而
monitorexit 是 插 入 到 方 法 结 束 处 和 异 常 处 , JVM 要 保 证 每 个
monitorenter 必须有对应的 monitorexit 与之匹配
查看汇编情况 :
// Step 1 : 准备简单的 Demo
public class SynchronizedService {
public void method() {
synchronized (this) {
System.out.println("synchronized 代码块");
}
}
}
// Step 2 : 查看汇编码
javap -c -s -v -l SynchronizedService.class
// Step 3 : 注意其中 3 和 13 以及 19
public void method();
descriptor: ()V
flags: ACC_PUBLIC
Code:
stack=2, locals=3, args_size=1
0: aload_0
1: dup
2: astore_1
3: monitorenter
剩余143页未读,继续阅读
资源评论
Andy&lin
- 粉丝: 97
- 资源: 214
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功