この質問は、整数値の同期に基づいてい ます。
から値を削除する方法に関する懸念に対処しない小さな問題があるだけで、解決策は優れているようですConcurrentHashMap
。
それで、私がプログラムの下で行ったことに対処するために
import java.util.concurrent.ConcurrentHashMap;
public class Example {
private final ConcurrentHashMap<Integer, Integer> concurrentHashMap = new ConcurrentHashMap<Integer, Integer>();
public void doSomething(int i) {
synchronized (getLockForId(i)) {
concurrentHashMap.remove(i);
}
}
public Integer getLockForId(int id) {
concurrentHashMap.putIfAbsent(id, id); // I want to replace these two
// operation with single one
// since it seems the cause of
// NPE
return concurrentHashMap.get(id);
}
public static void main(String[] args) {
final Example example = new Example();
new Thread(new Runnable() {
@Override
public void run() {
int i = 0;
while (true) {
example.doSomething(++i);
}
}
}).start();
new Thread(new Runnable() {
@Override
public void run() {
int i = 0;
while (true) {
example.doSomething(++i);
}
}
}).start();
}
}
問題は、結果が常に になることNullPointerException
です。私の最初の分析は、null に割り当てられた値を削除しているため、NullPointerException
. だから私は以下にしました
Object obj = new Object();
synchronized (obj) {
obj = null;
}
しかし、上記は結果になりませんNullPointerException
。私の質問は、なぜNullPointerException
上記のケースで投げているのですか?
しても
public Integer getLockForId(int id) {
return concurrentHashMap.putIfAbsent(id, id);
}
NullPointerException
他に1つの戻り値がある場合にのみ値を返すため、それでも結果が返されますnull