当线程1具有对象的内部锁时,
synchronized(object) {
...
}有没有可能打电话给
object.method()在线程2中,我是否需要分别键入
synchronized(object) {
object.method();
}在线程2中阻止它在线程1持有锁时调用方法?
在我的例子中,我在迭代map时获得了ConcurrentModificationExceptions,并且我试图通过锁定Map来防止来自其他线程的修改。我知道ConcurrentModificationExceptions的原因通常是因为映射在迭代过程中发生了变化,但我非常确定在我的例子中并非如此,因为在迭代中只有"get"-statements和一个方法调用,所以不会发生任何修改。
提前谢谢。
比纳比克
发布于 2011-10-02 19:26:52
Java中的同步是完全协作的--如果第二个线程不选择尝试获取监视器(如果尝试获取监视器的方法中没有任何内容),那么它不会自动锁定。
这并不是说对象“被锁定”了--而是一个线程拥有与该对象相关的锁。对象本身仍然可以被访问;如果它不需要锁,它就不会阻塞。
请注意,如果您尝试迭代ConcurrentModificationException并在同一个循环中更改它,您甚至可以在单个线程中获得它,例如
// Not safe: will throw an exception
for (Map.Entry<String, String> entry : map.entrySet()) {
if (entry.getKey().equals("foo")) {
map.put("bar", "Hello");
}
}这可能是你的代码中发生的事情,但我们不能确定,因为你没有向我们展示任何代码。如果你能提供一个简短但完整的程序来演示这个问题,我们就更有可能弄清楚到底是怎么回事。
发布于 2011-10-02 19:27:36
当您获取一个锁时,它只会阻止其他线程获取相同的锁。它本身并不锁定对象,您可以访问它的方法。
如果你有一个ConcurrentModicationException,那么你就有一个并发修改。如果你不知道这是在哪里发生的,你需要进一步调查。
发布于 2011-10-02 19:26:43
除非同步了object.method(),否则可以从其他线程调用它。在非同步映射上使用迭代时,您必须小心。您应该使用同步的map并在迭代中进行同步;否则,您还必须同步所有的写入操作。
https://stackoverflow.com/questions/7626028
复制相似问题