Java对象分配和锁定
考虑以下代码段:Java对象分配和锁定,java,synchronization,locking,Java,Synchronization,Locking,考虑以下代码段: Object bar1 = new ... ; Object bar2 = new ... ; Object foo = (either bar1 or bar2) ; 现在,在程序的不同时间,foo可以是bar1或bar2。我只是想检查synchronized(foo)是否会锁定相应的bar1或bar2。考虑到Java中没有复制对象,这似乎是最有可能的情况。这是正确的吗 Object bar1 = new Object(); Object foo = ba
Object bar1 = new ... ;
Object bar2 = new ... ;
Object foo = (either bar1 or bar2) ;
现在,在程序的不同时间,foo可以是bar1或bar2。我只是想检查synchronized(foo)是否会锁定相应的bar1或bar2。考虑到Java中没有复制对象,这似乎是最有可能的情况。这是正确的吗
Object bar1 = new Object();
Object foo = bar1;
synchronized(foo) {
...
}
将锁定foo
==bar1
然而,这是一个奇怪且容易出错的构造。例如:
- 线程1到达方法中,并且foo==bar1
- 线程1到达同步块并锁定bar1
- 线程2到达方法中,并且foo==bar2
- 线程2到达同步块并锁定bar2
另请参见。是。您不是在引用上同步,而是在底层对象上同步 每个对象都有一个关联的监视器,当您使用
synchronized
时,您将锁定该监视器。发件人:
在Java虚拟机中,每个对象和类在逻辑上都是
与监视器关联的。对于对象,关联的监视器
保护对象的实例变量。上课时,班长
保护类的类变量
是的,它将锁定
foo
指向的任何对象。但是,我强烈建议您将foo
设置为final,以避免出现以下情况:
Object foo = bar1;
synchronized(foo) {
foo = bar2;
}
因为它会导致havok,多个线程会看到不同的锁。另请参见此问题:+1一般来说,除了
最终
字段之外,同步任何内容都不是一个好主意。如果bar1
或bar2
需要同步,则应在内部同步。