为什么说hashmap是线程不安全的_map线程不安全

为什么说hashmap是线程不安全的_map线程不安全 hashMap线程不安全的原因及表现hashMap出现线程不安全的原因:HashMap的实现里没有锁的机制,因此它是线程不安全的。其实只要有锁的机制,可以通过锁实现线程安全,我们在读写HashMap对象的时候加锁,以保障这个对象的线程安全,但不代表HashMap本身是线程安全的,因为是外力(你自己加的锁)使然。为啥不在HashMap内部加锁让它变成线程安全?这…

大家好,又见面了,我是你们的朋友全栈君。如果您正在找激活码,请点击查看最新教程,关注关注公众号 “全栈程序员社区” 获取激活教程,可能之前旧版本教程已经失效.最新Idea2022.1教程亲测有效,一键激活。

Jetbrains全系列IDE稳定放心使用

hashMap出现线程不安全的原因:

HashMap的实现里没有锁的机制,因此它是线程不安全的。

其实只要有锁的机制,可以通过锁实现线程安全,我们在读写HashMap对象的时候加锁,以保障这个对象的线程安全,但不代表HashMap本身是线程安全的,因为是外力(你自己加的锁)使然。

为啥不在HashMap内部加锁让它变成线程安全?
这样会增加单线程访问的资源消耗,即使没有多线程访问,也要每次检查、加锁、解锁。
实际上有线程安全的Map,Collections里面有个静态方法可以返回一个线程安全版本的HashMap

public static <K,V> Map<K,V> synchronizedMap(Map<K,V> m) {

return new SynchronizedMap<K,V>(m);
}

另外java5之后还提供了ConcurrentHashMap类,提供更高效的线程安全操作。

hashMap出现线程不安全的表现:
表现1:

多个线程同时操作一个hashmap就可能出现不安全的情况:

比如A B两个线程(A线程获数据 B线程存数据) 同时操作myHashMap

1.B线程执行存放数据

modelHashMap.put(“1″,”2”);

2.A线程执行get获取数据

modelHashMap.get(“1”)

A线程获取的值本来应该是2,但是如果A线程在刚到达获取的动作还没执行的时候,

线程执行的机会又跳到线程B,此时线程B又对modelHashMap赋值 如:modelHashMap.put(“1″,”3”);

然后线程虚拟机又执行线程A,A取到的值为3,这样map中第一个存放的值 就会丢失。。。。。

要保证值的准确,就要保证操作的原子性,就是保证A操作从头开始不能被打断。。所有要用同步关键字,或者使用java 1.5中的current新包中的ConcurrentHashMap,这是线程安全的,在java最新的并发包中,对之前非线程安全的工具,如hashMap List 都做了同步封转。

表现2:

一般我们声明HashMap时,使用的都是默认的构造方法:HashMap<K,V>,看了代码你会发现,它还有其它的构造方法:HashMap(int initialCapacity, float loadFactor),其中参数initialCapacity为初始容量,loadFactor为加载因子,而之前我们看到的threshold = (int)(capacity * loadFactor); 如果在默认情况下,一个HashMap的容量为16,加载因子为0.75,那么阀值就是12,所以在往HashMap中put的值到达12时,它将自动扩容两倍,如果两个线程同时遇到HashMap的大小达到12的倍数时,就很有可能会出现在将oldTable转移到newTable的过程中遇到问题,从而导致最终的HashMap的值存储异常。

表现3:

构造entry<K,V>单链表时,也会出现不安全的情况。

原文: https://blog.csdn.net/VIP_WangSai/article/details/70182933

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-用户IM,转载请注明出处:https://javaforall.cn/183994.html原文链接:https://javaforall.cn

【正版授权,激活自己账号】: Jetbrains全家桶Ide使用,1年售后保障,每天仅需1毛

【官方授权 正版激活】: 官方授权 正版激活 支持Jetbrains家族下所有IDE 使用个人JB账号...

(0)


相关推荐

  • 前端框架AdminLTE

    前端框架AdminLTE作为CMDB资产管理项目,必须有一个丰富、直观、酷炫的前端页面。适合运维平台的前端框架有很多,开源的也不少,这里选用的是AdminLTE。AdminLTE托管在GitHub上,可以通过下面的地址下载:https://github.com/almasaeed2010/AdminLTE/releasesAdminLTE自带JQuery和Bootstrap3框架,无需另外下载。AdminLTE自带多种配…

  • WrapPanel水平布局保持不换行的写法示例[通俗易懂]

    WrapPanel水平布局保持不换行的写法示例[通俗易懂]UI需求宽高:235px*285px内容宽度:191px要求:每行2个,右边距15,下边距10代码写法:测量后发现两个item+margin=191,所以让wrappanel定宽191item中grid套个border,在border中设置左右间距7.5,这样两个元素加起来的宽就是15,由于左边距多了7.5,所以在上一层grid左缩进7.5拉回来就可以了效果:…

  • kali mysql 卸载,linux mysql卸载命令

    kali mysql 卸载,linux mysql卸载命令想知道linux下怎么完全删除或者卸载mysql吗?下面由学习啦小编为大家整理了linuxmysql卸载命令,希望大家喜欢!linuxmysql卸载命令一、用root用户删除mysql软件1、先查看mysql安装的rpm#rpm-aq|grep-imysqlMySQL-client-advanced-5.6.16-1.el6.x86_64MySQL-devel-advanced-5.6…

  • 上海主要地标经纬度「建议收藏」

    上海主要地标经纬度「建议收藏」金茂大厦经纬度:(121.50109,31.23691)国际会议中心经纬度:(121.49203,31.24149)上海体育馆经纬度:(121.43348,31.18334)龙华机场经纬度:(121.

  • noip2015_noip2021复赛

    noip2015_noip2021复赛扩展欧几里得模板题。注意取模。#include&lt;bits/stdc++.h&gt;usingnamespacestd;#definelllonglong#definein(x)scanf("%d",&amp;x)#definelin(x)scanf("%lld",&amp;x)#defineout(x)printf("%d",x)#defin…

  • java 线程池面试题

    java 线程池面试题Java多线程面试问题 1.进程和线程之间有什么不同? 一个进程是一个独立(selfcontained)的运行环境,它可以被看作一个程序或者一个应用。而线程是在进程中执行的一个任务。Java运行环境是一个包含了不同的类和程序的单一进程。线程可以被称为轻量级进程。线程需要较少的资源来创建和驻留在进程中,并且可以共享进程中的资源。2.多线程编程的好处是什么?  在多线程程序中,多个线程被

发表回复

您的电子邮箱地址不会被公开。

关注全栈程序员社区公众号