JAVA的ReentrantLock与synchronized 的区别
实现原理1.synchronized是虚拟机实现的,主要通过JVM中定义的监视器模型来实现。JVM的指令:OpcodeOperand(s)Descriptionmonitorenternonepop objectref, acquire the lock associated with objectrefmonitorexitnonepop o
实现原理
1.synchronized是虚拟机实现的,主要通过JVM中定义的监视器模型来实现。
JVM的指令:
Opcode | Operand(s) | Description |
---|---|---|
monitorenter | none | pop objectref, acquire the lock associated with objectref |
monitorexit | none | pop objectref, release the lock associated with objectref |
When monitorenter is encountered by the Java virtual machine, it acquires the lock for the object referred to by objectref on the stack. If the thread already owns the lock for that object, a count is incremented. Each time monitorexit is executed for the thread on the object, the count is decremented. When the count reaches zero, the monitor is released.
说明:进入和退出通过count来进行控制,JVM虚拟机规定,一个线程拥有锁,其他线程只能等这个线程退出才能拥有。同一线程对同一对象多次锁,增加count数量即可
2.lock是jdk中实现的,增加了锁队列,使用LockSupport.unpark和原子操作来实现
相同点
都可重入,高效的锁
区别
- ReentrantLock 的锁在jdk实现,有多重等待方法。synchronized只有一种,无超时,重试等等待方法
- synchronized是JVM实现,异常会自动释放;ReentrantLock 必须finally手动释放
- 竞争不激烈的情况下,synchronized优于ReentrantLock ,竞争激烈的情况下ReentrantLock 效果更好,详细报告见:http://lycog.com/concurency/performance-reentrantlock-synchronized/
- 锁出现问题的时候,JVM的日志对synchronized支持的好,ReentrantLock 支持的不好
应用场景
- 资源竞争激烈的情况下用ReentrantLock ,争取不到资源线程可以释放进行sleep,减少cpu消耗
- 进程通信复杂的,使用ReentrantLock和条件变量比较好,synchronized实现太复杂
- 简单的并且竞争不激烈的资源synchronized不错
参考
http://www.javaworld.com/article/2076971/java-concurrency/how-the-java-virtual-machine-performs-thread-synchronization.html
http://lycog.com/concurency/performance-reentrantlock-synchronized/
http://stackoverflow.com/questions/9072422/difference-between-synchronized-and-reentrantlock-pros-and-cons
http://stackoverflow.com/questions/11600520/synchronized-vs-reentrantlock-on-performance
更多推荐
所有评论(0)