偏向锁

偏向锁

概念

偏向锁是Java 6之后加入的新锁,它是一种针对加锁操作的优化手段,经过研究发现,在大多数情况下,锁不仅不存在多线程竞争,而且总是由同一线程多次获得,因此为了减少同一线程获取锁(会涉及到一些CAS操作,耗时)的代价而引入偏向锁。

mark word 和 monitor
  • mark word (实现偏向锁、轻量级锁关键)

如图可以看出,对象头中的Mark Word(标记字)主要用来表示对象的线程锁状态,另外还可以用来配合GC、存放该对象的hashCode;
在这里插入图片描述

  • monitor (重量锁实现)
    实际上,每个java对象都带了一把看不见的锁,我们俗称monitor锁或者内部锁
    主要字段说明:
    1.Owner字段:初始时为NULL表示当前没有任何线程拥有该monitor record,当线程成功拥有该锁后保存线程唯一标识,当锁被释放时又设置为NULL
    2.EntryQ字段:关联一个系统互斥锁(semaphore),阻塞所有试图锁住monitor record失败的线程
    3.RcThis字段:表示blocked或waiting在该monitor record上的所有线程的个数
    4.Nest字段:用来实现重入锁的计数
    5.HashCode字段:保存从对象头拷贝过来的HashCode值(可能还包含GC age)
    6.Candidate字段:用来避免不必要的阻塞或等待线程唤醒,因为每一次只有一个线程能够成功拥有锁,如果每次前一个释放锁的线程唤醒所有正在阻塞或等待的线程,会引起不必要的上下文切换(从阻塞到就绪然后因为竞争锁失败又被阻塞)从而导致性能严重下降;Candidate只有两种可能的值0表示没有需要唤醒的线程1表示要唤醒一个继任线程来竞争锁
    Monitor具体是怎么实现的?
    1.Monitor是在jvm底层实现的,底层代码是c++
    2.Monitor的enter方法:获取锁
    3.Monitor的exit方法:释放锁
    4.Monitor的wait方法:为java的Object的wait方法提供支持
    5.Monitor的notify方法:为java的Object的notify方法提供支持
    6.Monitor的notifyAll方法:为java的Object的notifyAll方法提供支持
实现原理

线程A访问同步代码块,检查mark word中是否存在了线程Aid,没有直接cas操作替换线程id,将偏向锁状态改成1;之后如果线程A再次访问同步代码块,获取到mark word中线程id是当前id,则直接执行代码块;
线程B访问同步代码块,访问到mark word中线程id不是当前线程id,查看持有锁的线程状态,如果不存活,直接cas替换,如果存活即发生了锁竞争,升级为轻量级锁
在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值