マルチスレッドプログラムで ConcurrentHashMap を使用しています。マップは、サーバーに関する詳細情報 (オンラインかどうか、最近の使用量など) を含むオブジェクトに ServerID をマップします。ServerID と ServerInformation はどちらも不変です。
サーバー情報を更新するために、この質問でポイント B) として提案されていることを多かれ少なかれ行っています: ConcurrentHashMap の値を変更するための推奨される方法は何ですか?
すなわち(私自身の変数名を使用するように変更されています)これ:
public void addUsage(ServerID id, long moreUsage) {
ServerInfo oldInfo = serverMap.get(id);
ServerInfo newInfo = oldInfo.addUsage(moreUsage);
serverMap.put(id, newInfo);
}
ここで私の質問は次のとおりです。更新が失われる可能性を排除するために、このメソッドを同期するべきではありませんか?
または、それを達成する別の方法はありますか?おそらく次のようなものです(明らかな間違いを取り除くために元のバージョンから編集されています):
public void addUsage(ServerID id, long moreUsage) {
ServerInfo oldInfo = serverMap.get(id);
ServerInfo newInfo = oldInfo.addUsage(moreUsage);
while (!serverMap.replace(id, oldInfo, newInfo) ) {
oldInfo = serverMap.get(id);
newInfo = oldInfo.addUsage(moreUsage);
// try again later
Thread.sleep(SOME_TIME);
};
}