为了账号安全,请及时绑定邮箱和手机立即绑定

Hashmap 删除指定key,线程安全?

Hashmap 删除指定key,线程安全?

翻阅古今 2019-04-04 13:19:33
http://m.blog.csdn.net/article/details?id=8960667 这篇文章第二点,关于删除指定key对应entry,不是线程安全的?为什么?看不太明白
查看完整描述

2 回答

?
慕工程0101907

TA贡献1887条经验 获得超5个赞

我大致看了下,我的理解是这样的。

当多个线程同时操作同一个数组位置的时候,也都会先取得现在状态下该位置存储的头结点,然后各自去进行计算操作,之后再把结果写会到该数组位置去,其实写回的时候可能其他的线程已经就把这个位置给修改过了,就会覆盖其他线程的修改

原文说当多个线程操作同一个数组位置,有可能是这样一种情况,比如两个线程,线程A要删除节点A,线程B要删除节点B,正好节点A和节点B都在同一个数组位置的链表中,然后两个线程都拿到了这个相同的数组位置,假设这个位置的链表是这样的header->A->B->C,那么线程A要做的是把header指向节点B就把节点A删掉了;线程B呢,是要把节点A指向节点C就把节点B删掉了;如果线程B先执行,线程A再执行,会发现节点B本来被线程B删掉了,然后又被线程A给弄回来了。


查看完整回答
反对 回复 2019-04-18
?
天涯尽头无女友

TA贡献1831条经验 获得超9个赞

final Entry<K,V> removeEntryForKey(Object key) {


    int hash = (key == null) ? 0 : hash(key.hashCode());

    int i = indexFor(hash, table.length);

    Entry<K,V> prev = table[i];

    Entry<K,V> e = prev;


    while (e != null) {

        Entry<K,V> next = e.next;

        Object k;

        if (e.hash == hash &&

            ((k = e.key) == key || (key != null && key.equals(k)))) {

            modCount++;

            size--;

            if (prev == e)

                table[i] = next;

            else

                prev.next = next;

            e.recordRemoval(this);

            return e;

        }

        prev = e;

        e = next;

    }


    return e;

}

如果两个线程同时进入这个方法,取得的i值相等的时候,一个线程的处理结果会被另一个处理结果覆盖。


查看完整回答
反对 回复 2019-04-18
  • 2 回答
  • 0 关注
  • 2598 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信