JavaConcurrentMap
には がありremove(key, expectedValue)
、これは次のいずれかを返します。
- 期待値はそこにあり、削除されました。
- 期待値がなかったので、削除されていません。
しかし、私が取得したいのは次のいずれかです。
- 期待値はそこにあり、削除されました。
- そのキーの下に値がありますが、予期されたものではないため、削除されていません。
- そのキーの下には値がないため、削除されていません。
この情報を並行かつスレッドセーフな方法で取得するにはどうすればよいですか?
これは私が安全にしようとしているコードです
// attempt to remove the old session...
if (!sessions.remove(player.getId(), existing)) {
// it was not removed...
if (sessions.containsKey(player.getId())) { // TODO threadsafe
// ...because in the meantime some other thread logged in as that user
throw new ServiceError(LobbyService.ERR_LOGIN_INVALID, Maps.create("reason", "already-logged-in"));
} else {
// ...because it was no longer there, which is as it should be
}
} else {
// it was removed, which is bad, because it shouldn't have been there still
log.warn("Kicking old session of " + player.getId() + " failed");
}
または一般化:
if (!sessions.remove(key, expected)) {
if (sessions.containsKey(key)) { // TODO threadsafe
// 2
} else {
// 3
}
} else {
// 1
}