参考:https://www.cnblogs.com/mingyueyy/p/13054296.html
https://www.cnblogs.com/aspirant/p/11470858.html
在Java中,锁的状态总共有四种,级别由低到高依次为:无状态锁、偏向锁、轻量级锁、重量级锁,这四种锁状态分别代表什么,为什么会有锁升级?其实在 JDK 1.6之前,synchronized 还是一个重量级锁,是一个效率比较低下的锁,但是在JDK 1.6后,Jvm为了提高锁的获取与释放效率,对(synchronized )进行了优化,引入了 偏向锁 和 轻量级锁 ,从此以后锁的状态就有了四种(无锁、偏向锁、轻量级锁、重量级锁),并且四种状态会随着竞争的情况逐渐升级,而且是不可逆的过程,即不可降级,也就是说只能进行锁升级,不能锁降级。这种锁升级却不能降级的策略,目的是为了提高获得锁和释放锁的效率。
锁的升级过程: 当多个线程抢占同一资源时,其中某个线程获得到一个偏向锁,这时如果过来其他线程也访问这个共享资源,这时偏向锁会升级为轻量级锁,当其他线程再次尝试访问资源后,轻量级锁会升级为自旋锁,这时其他线程不会再主动获得资源,而是由锁自旋,看自己的锁是否被释放掉,如果释放掉了他会通知其他线程来获得锁,如果多次自旋后自己的锁还是没有被释放则升级为重量级锁,这时其他线程会被挂起。锁升级过程适用于低并发,当高并发时其他线程应直接被挂起。
为什么会有这四种锁机制,因为在多线程并发的过程中,如果一个线程持有锁且很快就要执行完成,另一个线程来临,如果让第二个线程阻塞的话,代价有点大,要重新走到就绪–>运行状态中去。所以,出现了这四种锁机制。
偏向锁: 当一个线程访问对象时,它会偏向这个线程,此时对象持有偏向锁。偏向此时访问它的第一个线程,这个线程将对象头中的ThreadID改为自己的ID,之后再次访问这个对象的时候,只需要对比ID,不需要再使用CAS