假设我有两个哈希映射hashMap1和hashMap2,以及一个多线程并发Java程序.如果我放置一个同步块
synchronized(hashMap1) {
hashMap1.put(5, "Hello");
hashMap2.put(10, "Hi");
}
由于一次只有一个线程可以访问hashMap1,因此只有一个线程可以访问hashMap2吗?我本质上是在询问hashMap2是否将受到保护,避免像hashMap1一样被多个线程一次访问.
谢谢!
解决方法:
不,同步不会“锁定对象”.您的代码块要做的是,需要一个线程对hashMap1进行锁定,然后它才能进入该块. hashMap1本身不以任何方式“锁定”,除了正在获取其监视器. (也许将它称为监视器而不是锁.)监视器是所有对象都拥有的东西,它本身并没有做任何事情来控制对其所属对象的访问.如果在其他地方访问hashMap2,则此同步块将无济于事.
同步块的目的是要求线程获取监视器.您希望保护该资源免受并发访问的所有地方都需要使用相同的锁.同步告诉受保护的代码块何时需要使用锁定对象来控制访问.
监视器的选择可以与实际对象分离,以防止并发访问.您可以拥有一个专用的锁对象并使用它,而不要求必须在要保护的事物上使用锁. (唯一的好处是,它可能对组织有所帮助,如果您仅访问一件事,则使用该东西的监视器可能会很方便.)使用专用锁可能更清楚:
public class Foo {
private final Object LOCK = new Object();
private Map hashMap1 = new HashMap();
private Map hashMap2 = new HashMap();
public void doStuff() {
synchronized(LOCK) {
... // do stuff with hashMap1 and hashMap2
}
}
}
保持对对象私有的锁访问权限意味着对象可以限制谁可以获取锁(与synced(this)不同).也不要使用诸如String或Boolean之类的东西,它们可以被插入,缓存或从程序的其他部分进行访问.
标签:multithreading,synchronized,java
来源: https://codeday.me/bug/20191028/1955729.html