Java锁机制

问:为何说java的syncronized关键字的效率很低? java

这是由于,java中线 程是映射到操做系统的原生线程上的。若是要唤醒或者是阻塞一条线程须要操做系统的帮忙。这就须要从用户态转换到核心态。所以,状态转换须要至关长的时间。 因此说syncronized关键字是java中比较重量级的操做。虚拟机自己会作一些优化。好比,在通知操做系统阻塞线程以前,加入一段自旋等待过程, 避免频繁的切入到和心态中。 安全

除了syncronized关键字,java中还可使用java.lang.concurrent包中的ReentrantLock来实现同步。在基本用法上,两者相似。可是ReentrantLock增长了一些高级特性,只要有如下三个: 多线程

第1、等待可中断 jvm

第2、公平锁 函数

第3、锁绑定多个条件 性能

等待可中断是指,等待的线程在等待超过必定时间以后,能够选择继续等待,或者也能够不等待直接去作其余事情了。这对于执行时间很是长的同步块来讲颇有用。 优化

公平锁是指,线程必须按照排队的顺序来得到锁,而非公平锁则不保证这一点。在非公平锁中,任何一个等待的线程都有可能得到锁。 spa

锁绑定多个条件是指,一个 ReentrantLock对象能够同时绑定多个Condition对象。而在syncronized中,锁对象的wait和notify或者是 notifyall方法能够实现一个隐含的条件,若是要和多于一个的条件进行关联的时候,则不得不额外的添加一个锁。ReentrantLock不须要额 外的添加一个锁,只须要屡次调用newCondition()方法便可。 操作系统

与syncronized相比,ReentrantLock的性能能够保持在一个比较稳定的水平。从java1.6开始,syncronized与ReentrantLock在性能上彻底持平了。因此在1.6以后,性能就不是选择ReentrantLock的缘由了。 线程

---------------------------------------------------------------------------------------

锁的优化

jvm针对锁进行了一些优化

第1、自旋锁和自适应自旋

第2、锁消除

第3、锁粗化

第4、轻量级锁

第5、偏向锁

其中,自旋锁,是指线程在等待一个锁的时候,不放弃cpu时间,而是在忙等。这个功能是有缺点的,好比说,等待时间过长,那么自旋只会白白浪费cpu时间。若是等待时间很短,那么自旋却是颇有价值。

自适应自旋锁因而诞生了。若是上一次自旋成功了,那么自适应自旋锁会认为下一次等待也应该会成功,因而能够适当的放宽自旋的等待时间。若是以前一直自旋失败,那么会省掉这个自旋过程,直接进入线程挂起。

锁消除是指,根据代码逃逸技术,若是判断到一段代码中,堆上的数据不会逃逸出当前线程,那么能够认为这段代码是线程安全的,没必要要加锁好比说String a="a"+"b",这段代码中实际上是有锁的【想一想StringBuffer】,可是编译器把锁给优化掉了。

锁粗化,什么是粗化??好比说String a="a"+"b"+"c",这里实际上是有多个锁操做的。可是在同一个函数里面,是没有代码竞争的,根本就没有必要进行锁操做。因而,编译器就能够优化掉这部分锁操做。

轻量级锁,是JDK1.6新增的锁机制。这里的轻量级是针对须要操做系统互斥量来实现的传统锁而言的。所以传统的锁被称做是“重量级锁”。轻量级锁并非用来取代重量级锁的,他的本意是在没有多线程竞争的状况下,减小传统的重量级锁使用操做系统互斥量产生的性能损耗。

偏向锁,也是1.6才引入的一项锁优化。目的是为了消除数据在无竞争的状况下的同步原语。进一步提升程序的性能。偏 向锁就是“偏袒”第一个得到这个锁的线程,若是在接下来的执行过程当中,该锁没有被其余线程获取,那么该线程将永远不须要再次进行同步。可是当另一个线程 尝试获取该锁的时候,偏向模式宣告结束。根据锁定对象的当前状态,撤销偏向后恢复到未锁定状态或者是进入轻量级锁定状态。能够看出,若是程序中大多数的锁 都是被多个线程所访问的,那么偏向锁就是多余的。

相关文章
相关标签/搜索