提供以下代码
class Test{
double x;
public void synchronized a()
{
x = 0;
//do some more stuff
}
public void b()
{
x = -1;
}
}
在修改x的中间的()中的线程是否可以被一个在同一个对象上调用b()的线程抢占?
是不是像单个原子操作一样执行同步方法?
我相信另一种方式是可能的(b()中的线程可以被调用同一对象上的()的线程抢占,因为b()没有保护我的Test对象锁。
有人可以对此有所了解吗?
答案 0 :(得分:11)
synchronized
仅阻止其他线程获取同一监视器。它在中没有使操作成为原子。特别是:
b()
未同步,因此一个线程完全可以执行a()
而另一个线程可以同时执行b()
。
答案 1 :(得分:0)
由于b()
未同步且a()
已同步,因此一个帖子可能位于a()
而另一个位于b()
。因此,由于x
的并行非同步访问,x
的值很可能会出现乱码。
此外,如果您的代码是这样的:
class Test{
double x;
public void synchronized a()
{
x = 0;
//do some more stuff
}
public void b()
{
x = -1;
a(); //added call to a()
}
}
并且您的两个线程都在相同的实例上运行,然后出现线程1 [当前在a()
中被线程2抢占的可能性[目前在b()
]。
但是,在线程1被抢占后,当线程2尝试进入a()
方法时,JVM将不允许它;因为另一个线程[虽然是一个非运行的线程]已经锁定它。因此,现在线程2将等待,直到线程1完成a()
的执行并返回。然后线程2 [很可能]将恢复生命并允许执行a()
。