java中concurrenthashmap是线程安全的吗

 我来答
万课匈
2016-10-21 · 超过30用户采纳过TA的回答
知道答主
回答量:76
采纳率:0%
帮助的人:34.6万
展开全部
这样使用是有问题的。
ConcurrentMap能够保证每一次调用(例如一次putIfAbsent)都是原子操作,不受多线程影响,但并不保证多次调用之间也是原子操作。
以上实现的GetKeyBM方法中,ConcurrentMap的方法被调用了许多次,不同线程之间必然存在着竞争关系,导致最终结果不正确。

现在的目标是,将下面描述的这一系列操作作为原子操作:
“对每个分出来的词通过调用GetKeyBM方法,如果存在,则取出对应的编码,如果不存在,则加入KeyTotal中,并且给予一个编码,就是KeyTotal中的变量数加一”
最直观的方法就是整块同步:
synchronized (KeyTotal) {
Integer value = KeyTotal.get(word);
if (value == null) {
value = KeyTotal.size() + 1;
KeyTotal.put(word, value);
}
}
这样,使用普通的map就可以了。

如果你使用的是Java 8的话,ConcurrentMap有一个类似的方法 computeIfAbsent 可以使用:
KeyTotal.computeIfAbsent(word, k -> KeyTotal.size() + 1);
这样才能确保一次原子操作。
computeIfAbsent方法的作用是,如果word键值不存在,则使用第二个参数来生成一个值放入map中,等价于以下代码,并且是原子操作:
V computeIfAbsent(K key, Function<? super K,? extends V> mappingFunction):

if (map.get(key) == null) {
V newValue = mappingFunction.apply(key);
if (newValue != null)
return map.putIfAbsent(key, newValue);
}
正好与你的目标是一致的。
推荐律师服务: 若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询

为你推荐:

下载百度知道APP,抢鲜体验
使用百度知道APP,立即抢鲜体验。你的手机镜头里或许有别人想知道的答案。
扫描二维码下载
×

类别

我们会通过消息、邮箱等方式尽快将举报结果通知您。

说明

0/200

提交
取消

辅 助

模 式