What is the difference between the two synchronizations:
public synchronized void set (int i) {
this.i = i;
}
and
public void set (int i) {
synchronized (this) {
this.i = i;
}
}
What is the difference between the two synchronizations:
public synchronized void set (int i) {
this.i = i;
}
and
public void set (int i) {
synchronized (this) {
this.i = i;
}
}
第一个是同步方法,第二个是同步块。
在这里,当您synchronized
在块中的这个对象上时,它们都代表相同。在synchronized-method
线程中获取当前对象的锁。
注意:在同步块中,您可以同步代码块而不是整个方法体,以及使用不同的资源进行锁定(除了这个)。
这两种同步方法是等价的,因为你this
在synchronized block
.
同步基于Intrinsic Lock或Monitor Lock,每个 Object 的一个属性
正如其他答案所述,您的第一个命题是 a synchronized method
,这意味着线程将获取当前对象的锁。
来自 Oracle 教程:
当线程调用 a
synchronized method
时,它会自动获取该方法对象的内在锁,并在方法返回时释放它。即使返回是由未捕获的异常引起的,也会发生锁定释放。
你的第二个命题是synchronized block
or synchronized statement
。在这种情况下,线程获取放入参数的对象的锁。
再次来自 Oracle 教程:
与同步方法不同,同步语句必须指定提供内在锁的对象:
在您的情况下,您放置this
它会像同步方法一样锁定当前对象。
但是你也可以给它另一个对象,它会占用它的锁,而当前对象锁“不变”
synchronized(this)
被写入所以如果你把第二种方法写成
public void set (int i) {
// Code here is not synchronized
synchronized (this) { // only this block of code is synchronized
this.i = i;
}
// code after this is also not synchronized.
}
但是在第二个块的情况下,您也可以同步其他一些对象。
public void set (int i) {
synchronized (someObject) {
this.i = i;
}
}
它们是写同一件事的不同方式。Java 本来可以有第二种形式。在方法的this
对象上同步方法的整个主体是一种特别常见的情况,因此该语言提供了一种快速、简单的方法。
Java 语言规范在8.4.3.6 同步方法中声明了等效性。synchronized void bump() { count++; }
具有完全相同的效果
void bump() {
synchronized (this) {
count++;
}
}
两种同步没有区别,但第二种更灵活:可以在synchronized
块外以相同的方法添加不同步的代码,或者在不同于this
.