syschronized的使用、原理以及与重入锁ReenTrantLock的比较

syschronized的使用

(1)确保线程互斥的访问同步代码 
(2)保证共享变量的修改能够及时可见 
(3)有效解决重排序问题

从语法上讲,Synchronized总共有三种用法: 
  (1)修饰普通方法 
4 public synchronized void method1(){ 
5 System.out.println(“Method 1 start”); 
6 try { 
7 System.out.println(“Method 1 execute”); 
8 Thread.sleep(3000); 
9 } catch (InterruptedException e) { 
10 e.printStackTrace(); 
11 } 
12 System.out.println(“Method 1 end”); 
13 } 
14 
  (2)修饰静态方法 
public static synchronized void method1(){ 
5 System.out.println(“Method 1 start”); 
6 try { 
7 System.out.println(“Method 1 execute”); 
8 Thread.sleep(3000); 
9 } catch (InterruptedException e) { 
10 e.printStackTrace(); 
11 } 
12 System.out.println(“Method 1 end”); 
13 }

  (3)修饰代码块 
4 public void method1(){ 
5 System.out.println(“Method 1 start”); 
6 try { 
7 synchronized (this) { 
8 System.out.println(“Method 1 execute”); 
9 Thread.sleep(3000); 
10 } 
11 } catch (InterruptedException e) { 
12 e.printStackTrace(); 
13 } 
14 System.out.println(“Method 1 end”); 
15 }

syschronized的原理

4 public void method() { 
5 synchronized (this) { 
6 System.out.println(“Method 1 start”); 
7 } 
8 }

反编译以上代码得 
这里写图片描述
monitorenter : 
每个对象有一个监视器锁(monitor)。当monitor被占用时就会处于锁定状态,线程执行monitorenter指令时尝试获取monitor的所有权,过程如下: 
1、如果monitor的进入数为0,则该线程进入monitor,然后将进入数设置为1,该线程即为monitor的所有者。 
2、如果线程已经占有该monitor,只是重新进入,则进入monitor的进入数加1. 
3.如果其他线程已经占用了monitor,则该线程进入阻塞状态,直到monitor的进入数为0,再重新尝试获取monitor的所有权。

monitorexit: 
执行monitorexit的线程必须是objectref所对应的monitor的所有者。

通过这两段描述,我们应该能很清楚的看出Synchronized的实现原理,

Synchronized的语义底层是通过一个monitor的对象来完成,其实wait/notify等方法也依赖于monitor对象,这就是为什么只有在同步的块或者方法中才能调用wait/notify等方法,否则会抛出java.lang.IllegalMonitorStateException的异常的原因。

syschronized 与 lock(重入锁ReenTrantLock)

https://www.cnblogs.com/iyyy/p/7993788.html 
1.首先synchronized是java内置关键字,在jvm层面,Lock是个java类;

2.synchronized无法获得锁的状态,因此会自动释放锁。(a 线程执行完同步代码会释放锁 ;b 线程执行过程中发生异常会释放锁),Lock需要在finally中调用Unlock()手工释放。

3.用synchronized关键字的两个线程1和线程2,如果当前线程1获得锁,线程2线程等待。如果线程1阻塞,线程2则会一直等待下去,而Lock锁就不一定会等待下去,如果尝试获取不到锁,线程可以不用一直等待就结束了;

4.synchronized的锁可重入、不可中断、非公平,而Lock锁可重入、可中断、可公平、绑定多个Condition.(两者皆可重入) 
重入:可以再进入的锁。同一个线程每次进入一次,锁的计数器都自增1,所以要等到锁的计数器下降为0时才能释放锁。 
等待可中断:在持有锁的线程长时间不释放锁的时候,等待的线程可以选择放弃等待. tryLock(long timeout, TimeUnit unit) 
公平锁按照申请锁的顺序来一次获得锁称为公平锁. 
绑定多个Condition 通过多次newCondition可以获得多个Condition对象,可以简单的实现比较复杂的线程同步的功能.通过await(),signal();

5.Lock锁适合大量同步的代码问题,synchronized锁适合代码少量的同步问题。

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值