2021-06-22

Java synchronized对象级别与类级别的同步锁

Java synchronized 关键字 可以将一个代码块或一个方法标记为同步代码块。同步代码块是指同一时间只能有一个线程执行的代码,并且执行该代码的线程持有同步锁。synchronized关键字可以作用于

  • 一个代码块
  • 一种方法

当一个方法或代码块被声明为synchronized时,如果一个线程正在执行该synchronized 方法或代码块,其他线程会被阻塞,直到持有同步锁的线程释放。根据锁定的范围可以分为

  • 类级别的锁可以防止多个线程在运行时同时进入该类所有实例化对象的 synchronized代码块中。
  • 对象级别的锁可以防止多个线程在运行时同时进入当前(或某一个)实例化对象的 synchronized代码块中。

1. 对象级别的同步锁

对象级别的同步锁:当我们想要在多线程环境下同步执行一个非静态方法或非静态代码块时,在类的方法或代码块加上synchronized关键字,可以保证对象实例级别数据的线程安全。(比较后文的类级别的同步锁,回头来理解这句话)

对象级别的加锁的代码如下,如:在方法上加锁,锁对象为当前类的实例化对象

public class DemoClass{	public synchronized void demoMethod(){}}

如:为代码块加锁,锁对象为this对象

public class DemoClass{	public void demoMethod(){		synchronized (this){			//同步代码块		}	}}

如:为代码块加锁,锁对象为我们创建的任意一个对象。不要使用非final的成员变量作为同步锁对象,因为非final成员变量可以被重新赋值,导致不同的线程使用不同的对象作为锁,达不到同步锁定的效果。

public class DemoClass{ //注意这里的关键字final非常重要,看说明	private final Object lock = new Object();	public void demoMethod(){		synchronized (lock){			//同步代码块		}	}}

2. 类级别的同步锁

类级别的锁可以防止多个线程在运行时进入该类所有实例化对象的 "synchronized块中。也就是说如果运行时有100个DemoClass的实例,那么每次只有一个线程能够在任何一个实例中执行demoMethod(),所有其他实例的所有其他线程都被锁定。

为了保障静态数据线程安全,应该使用类级别的锁定。我们知道static关键字将方法的数据关联到类的级别上,所以在静态方法上使用锁。

静态方法加锁,对该类所有的实例化对象生效

public class DemoClass{	//静态方法加锁,对该类所有的实例化对象生效	public synchronized static void demoMethod(){	}}

获取 .class类的引用,类级别的锁

public class DemoClass{	public void demoMethod(){		//获取 .class类的引用,类级别的锁,对该类所有的实例化对象生效		synchronized (DemoClass.class){			//同步代码块		}	}}

使用静态对象的锁,类级别的锁

public class DemoClass{ //静态对象,类级别,注意这里的关键字final非常重要	private final static Object lock = new Object();	public void demoMethod(){		//使用静态对象的锁,类级别锁,对该类所有的实例化对象生效		synchronized (lock){			//同步代码块		}	}}

3. 总结

  1. Java中的同步机制保证了两个或多个线程无法同时执行一个需要相同同步锁的方法。
  2. "synchronized "关键字只能用于方法和代码块。这些方法或代码块可以是静态非静态的。
  3. 当一个线程进入synchronized方法或代码块时,它就会获得一个锁,当它离开同步方法或代码块时,它就会释放这个锁。如果线程执行过程出现任何错误或异常,锁也会被释放。
  4. 使用"synchronized "关键字持有的锁在本质上是可重入的,这意味着如果一个同步方法调用另一个使用相同锁的同步方法,那么持有锁的当前线程可以进入该方法而无需再次获得锁。
  5. 如果同步块中使用的对象为空,Java synchronized 将抛......

    原文转载:http://www.shaoqun.com/a/820633.html

    跨境电商:https://www.ikjzd.com/

    c88:https://www.ikjzd.com/w/1017

    myyearbook:https://www.ikjzd.com/w/726

    小马哥:https://www.ikjzd.com/w/1655


    Javasynchronized关键字可以将一个代码块或一个方法标记为同步代码块。同步代码块是指同一时间只能有一个线程执行的代码,并且执行该代码的线程持有同步锁。synchronized关键字可以作用于一个代码块一种方法当一个方法或代码块被声明为synchronized时,如果一个线程正在执行该synchronized方法或代码块,其他线程会被阻塞,直到持有同步锁的线程释放。根据锁定的范围可以分为
    洋老板:https://www.ikjzd.com/w/2779
    Dealdoktor:https://www.ikjzd.com/w/1603
    Sparblog:https://www.ikjzd.com/w/1604
    Dealbunny:https://www.ikjzd.com/w/1605
    装嫩or出轨 男人最恨8种女人(2/2):http://lady.shaoqun.com/m/a/40782.html
    tinypic:https://www.ikjzd.com/w/114
    3月,该去西藏了!5天打卡"春季最美桃花线"!:http://www.30bags.com/a/245857.html
    专家解读:婚后 为何老婆总是否定我:http://lady.shaoqun.com/a/13623.html
    男人经常㖭我的下面 亲爱的你那里的水好甜啊:http://lady.shaoqun.com/m/a/247977.html
    "都市情感故事范例":穿高跟鞋的女人和狗(2):http://www.30bags.com/a/448882.html
    Skyee获A股首家上市支付公司加持,引入战略投资成功!:https://www.ikjzd.com/articles/145907
    速卖通现在好做吗?精品才是王道!:https://www.ikjzd.com/articles/145902

No comments:

Post a Comment