• 一:java多线程互斥,和java多线程引入偏向锁和轻量级锁的原因?

--->synchronized的重量级别的锁,就是在线程运行到该代码块的时候,让程序的运行级别从用户态切换到内核态,把所有的线程挂起,让cpu通过操作系统指令,去调度多线程之间,谁执行代码块,谁进入阻塞状态。这样会频繁出现程序运行状态的切换,线程的挂起和唤醒,这样就会大量消耗资源,程序运行的效率低下。为了提高效率,jvm的开发人员,引入了偏向锁,和轻量级锁,尽量让多线程访问公共资源的时候,不进行程序运行状态的切换,由用户态进入内核态,借助操作系统进行互斥。
 
--->jvm规范中可以看到synchronized在jvm里实现原理,jvm基于进入和退出Monitor对象来实现方法同步和代码块同的。在代码同步的开始位置织入monitorenter,在结束同步的位置(正常结束和异常结束处)织入monitorexit指令实现。线程执行到monitorenter处,讲会获取锁对象锁对应的monitor的所有权,即尝试获得对象的锁。(任意对象都又一个monitor与之关联,当且一个monitor被持有后,他处于锁定状态)
 
--->java的多线程安全是基于lock机制实现的,而lock的性能往往不如人意。原因是,monitorenter与monitorexit这两个控制多线程同步的bytecode原语,是jvm依赖操作系统互斥(mutex)来实现的。
 
--->互斥是一种会导致线程挂起,并在较短时间内又需要重新调度回原线程的,较为消耗资源的操作。
 
--->为了优化java的Lock机制,从java6开始引入轻量级锁的概念。轻量级锁本意是为了减少多线程进入互斥的几率,并不是要替代互斥。它利用了cpu原语Compare-And-Swap(cas,汇编指令CMPXCHG),尝试进入互斥前,进行补救。
 
 
  • 五:偏向锁,轻量级锁,重量级锁对比

优点 缺点 适用场景
偏向锁 加锁和解锁不需要额外的消耗,和执行非同步方法相比仅存在纳秒级的差距 如果线程间存在锁竞争,会带来额外的锁撤销的消耗 适用于只有一个线程访问同步块场景
轻量级锁 竞争的线程不会阻塞,提高了程序的响应速度 如果始终得不到索竞争的线程,使用自旋会消耗CPU 追求响应速度,同步块执行速度非常快
重量级锁 线程竞争不使用自旋,不会消耗CPU 线程阻塞,响应时间缓慢 追求吞吐量,同步块执行速度较长

对象头的存储内容(monitor)

长度 内容 说明
32/64bit Mark Word 存储对象的hashcode或锁信息
32/64bit 类对象的地址 存储到对象类型数据的指针
32/64bit Array length 数组的长度(如果当前对象是数组)

Mark Word存储内容(monitor)的状态变化

锁状态 25bit,4bit 1bit(是否是偏向锁) 2bit(锁标示位)
轻量级锁 指向栈中锁记录的指针   00
重量级锁 指向互斥量(重量级锁)的指针   10
 GC   11
偏向锁 线程id,对象hashcode,对象分代年龄 1 01
  • 六:锁的状态

--->锁一共有四种状态(由低到高的次序):无锁状态,偏向锁状态,轻量级锁状态,重量级锁状态
--->锁的等级只可以升级,不可以降级。这种锁升级却不能降级的策略,目的是为了提高获得锁和释放锁的效率。
 
 
  • 七:偏向锁

--->a线程获得锁,会在a线程的的栈帧里创建lock record(锁记录变量),则在锁对象的对象头里和lock record里存储a线程的线程id.以后该线程的进入,就不需要cas操作,只需要判断是否是当前线程。
--->a线程获取锁,不会释放锁。直到b线程也要竞争该锁时,a线程才会释放锁。
--->偏向锁的释放,需要等待全局安全点(在这个时间点上没有正在执行的字节码),它会首先暂停拥有偏向锁的线程,然后检查持有偏向锁的线程是否还活着,如果线程不处于活动状态,则将对象头设置成无锁状态。如果线程仍然活着,拥有偏向锁的栈会被执行,遍历偏向对象的所记录。栈帧中的锁记录和对象头的Mark Word要么重新偏向其他线程,要么恢复到无锁,或者标记对象不适合作为偏向锁。最后唤醒暂停的线程。
--->关闭偏向锁,通过jvm的参数-XX:UseBiasedLocking=false,则默认会进入轻量级锁。
 
  • 八:轻量级锁

--->a线程获得锁,会在a线程的栈帧里创建lock record(锁记录变量),让lock record的指针指向锁对象的对象头中的mark word.再让mark word 指向lock record.这就是获取了锁。
--->轻量级锁,b线程在锁竞争时,发现锁已经被a线程占用,则b线程不进入内核态,让b线程自旋,执行空循环,等待a线程释放锁。如果,完成自旋策略还是发现a线程没有释放锁,或者让c线程占用了。则b线程试图将轻量级锁升级为重量级锁。
 
 
  • 九:重量级锁

--->重量级锁,就是让争抢锁的线程从用户态转换成内核态。让cpu借助操作系统进行线程协调。

Java 多线程之:偏向锁,轻量级锁,重量级锁的更多相关文章

  1. JAVA多线程之volatile 与 synchronized 的比较

    一,volatile关键字的可见性 要想理解volatile关键字,得先了解下JAVA的内存模型,Java内存模型的抽象示意图如下: 从图中可以看出: ①每个线程都有一个自己的本地内存空间--线程栈空 ...

  2. JAVA多线程之wait/notify

    本文主要学习JAVA多线程中的 wait()方法 与 notify()/notifyAll()方法的用法. ①wait() 与 notify/notifyAll 方法必须在同步代码块中使用 ②wait ...

  3. java多线程之yield,join,wait,sleep的区别

    Java多线程之yield,join,wait,sleep的区别 Java多线程中,经常会遇到yield,join,wait和sleep方法.容易混淆他们的功能及作用.自己仔细研究了下,他们主要的区别 ...

  4. Java多线程之Runnable与Thread

    Java多线程之Thread与Runnable 一.Thread VS Runnable 在java中可有两种方式实现多线程,一种是继承Thread类,一种是实现Runnable接口:Thread类和 ...

  5. Java多线程之synchronized详解

    目录 synchronized简介 同步的原理 对象头与锁的实现 锁的优化与升级 Monitor Record 锁的对比 synchronized简介 synchronized关键字,一般称之为&qu ...

  6. Java多线程之ConcurrentSkipListMap深入分析(转)

    Java多线程之ConcurrentSkipListMap深入分析   一.前言 concurrentHashMap与ConcurrentSkipListMap性能测试 在4线程1.6万数据的条件下, ...

  7. JAVA多线程之UncaughtExceptionHandler——处理非正常的线程中止

    JAVA多线程之UncaughtExceptionHandler——处理非正常的线程中止 背景 当单线程的程序发生一个未捕获的异常时我们可以采用try....catch进行异常的捕获,但是在多线程环境 ...

  8. java多线程之wait和notify协作,生产者和消费者

    这篇直接贴代码了 package cn.javaBase.study_thread1; class Source { public static int num = 0; //假设这是馒头的数量 } ...

  9. java多线程之:深入JVM锁机制2-Lock (转载)

    前文(深入JVM锁机制-synchronized)分析了JVM中的synchronized实现,本文继续分析JVM中的另一种锁Lock的实现.与synchronized不同的是,Lock完全用Java ...

随机推荐

  1. 【转】CSDN离线网页html文件自动跳转

    问题: 最近使用OneNote2016剪辑csdn的文章时,发现一些公式/文本框不能被正确识别,所以离线保存网页的html文件. 但是每次打开html文件,都会自动跳转的CSDN主页,即使断网,也会自 ...

  2. Ajax第一天——入门与基本概念

    什么是Ajax Ajax被认为是(Asynchronous JavaScript and XML的缩写).异步的js和xml 异步和同步:同步->类似打电话,接完一个再接下一个:异步:-> ...

  3. 20155236范晨歌_EXP3免杀原理与实践

    20155236范晨歌_免杀原理与实践 免杀 概述 免杀,也就是反病毒(AntiVirus)与反间谍(AntiSpyware)的对立面,英文为Anti-AntiVirus(简写Virus AV),逐字 ...

  4. 20145207 Exp9 web安全基础实践

    Exp9 web安全基础实践 实验后回答问题 (1)SQL注入攻击原理,如何防御 攻击原理:修改信息 防御:禁止输入 (2)XSS攻击的原理,如何防御 攻击原理:看别人的博客,感觉就是强制访问. 防御 ...

  5. sublime ruby [Decode error - output not utf-8] 错误

    今天用sublime3 写ruby,然后最简单的 pust "hello" 都出不来, ctrl + b的时候报错.注:win7下 [Decode error - output n ...

  6. [arc081F]Flip and Rectangles-[黑白染色]

    Description 传送门 Solution 有一个神秘的结论..我不知道大佬是怎么场上推出来的. 一个黑白染色图,每次可以任意翻转行或列的颜色,如果每个2*2的子矩阵内黑色格子都是偶数个,则可以 ...

  7. python+soket实现 TCP 协议的客户/服务端中文(自动回复)聊天程序

    [吐槽] 网上的代码害死人,看着都写的言之凿凿,可运行就是有问题. 有些爱好代码.喜欢收藏代码的朋友,看到别人的代码就粘贴复制过来.可是起码你也试试运行看啊大哥 [正文] 昨日修改运行了UDP协议的C ...

  8. python安装mysql

    一.MySQL是一种关系数据库管理系统,关系数据库将数据保存在不同的表中,而不是将所有数据放在一个大仓库内,这样就增加了速度并提高了灵活性. 二.最近在学习python语言,总体上面来说还是接触的挺快 ...

  9. 设置JFrame背景图片

    这里我就放上改写的代码吧,不做多的解释,推荐一个好的博文 https://blog.csdn.net/jdsjlzx/article/details/16831815 public void ini_ ...

  10. load和loads的区别

    相同点 load 和loads 都是实现"反序列化" 区别 1.loads loads针对内存对象 loads: 将 字符串 转换为 字典 # 这是一个字符串'{"b&q ...