synchronized与static synchronized的区别

来源:互联网 发布:德力西 知乎 编辑:程序博客网 时间:2024/04/20 17:06

synchronized关键字是Java支持的锁,始终要保证临界区的访问控制。所谓临界区就是指访问这个地方最多只有一个线程。Synchronized是通过在对象上加锁后进入临界区来达到临界区串行访问的目的,而对象本身的作用域将决定锁的粒度。

synchronized是对类的当前实例进行加锁,目的是防止其他线程同时访问该类的该实例的所有synchronized块。

static synchronized是限制线程同时访问JVM中该类的所有实例同时访问对应的代码块。

synchronized相对于this.synchronized,static synchronized相对于something.synchronized。

《Java多线程设计模式》中的一个例子:

public class Something{

public synchronized void isSyncA(){}

public synchronized void isSyncB(){}

public static synchronized void cSyncA(){}

public static synchronized void cSyncB(){}

}

假如Something类有两个实例x与y,下列组合是否可以被一个以上的线程同时访问?

A:x.isSyncA() 与x.isSyncB()

解析:都是对同一实例的synchronized域访问,因此不能被同时访问。

B:x.isSyncA()与y.isSyncA()

解析:是针对不同实例的,因此可以被同时访问。

C:x.cSynchA()与y.cSyncB()

解析:因为是static  synchronized,所以不同实例之间仍然会被限制,相当于Somthing.isSyncA()与Something.isSyncB(),因此不同被同时访问。

D:x.isSyncA()与Something.cSyncA()

解析:synchronized的是实例方法与synchronized的类方法由于锁定的是不同的,所以可以被同时访问。

结论:static synchronized是某个类的范围,synchronized static cSync(){} 防止多个线程同时访问这个类中的static synchronized方法。它可以对类的所有对象实例起作用。

synchronized是某实例的范围,synchronized isSync(){}防止多个线程同时访问这个实例中的synchronized方法。


Thinking in java的中文版本中,也有如下说明:

synchronized关键字的作用域如下两种:

(1)是某个对象实例内,synchronized aMethod(){}可以防止多个线程同时访问这个对象的synchronized方法(如果一个对象有多个synchronized方法,只要一个线程访问了其中的synchronized方法,其他线程不能同时访问这个对象中任何一个synchronized方法)。这时,不同的对象实例的synchronized方法是不相互干扰的。也就是说,其他线程照样可以同时访问相同类的另一个对象实例中的synchronized方法;

(2)是某个类的访问,synchronized static  aStaticmethod{}防止多个线程同时访问这个类中的synchronized static方法。它可以对类的所有对象实例起作用。

另外,除了在方法前用synchronized关键字,synchronized关键字还可以用于方法中的某个区块中,表示只对这个区块的资源实行互斥访问。用法是:synchronized(this){/*区块*/},它的作用域是当前对象。

synchronized关键字是不能继承的,也就是说,基类的方法synchronized f(){} 在继承类中并不自动是synchronized f(){},而是变成了f(){}。继承类需要显式的指定它的某个方法为synchronized方法。


这篇博文参考了:http://www.cnblogs.com/shipengzhi/articles/2223100.html

                   

0 0