HashMap以及ConcurrentHashMap(volatile)

本文探讨HashMap的实现,强调其利用hashCode和equals处理冲突,并解释为何需要重写这两个方法。同时,详细介绍了ConcurrentHashMap的线程安全实现,包括JDK7中的分段锁策略和JDK8的优化。最后,阐述了volatile关键字的作用,确保多线程环境下变量的可见性。
摘要由CSDN通过智能技术生成

1.HashMap怎么实现hashcode和equals

HashMap的数据结构是链表+数组,HashMap的数据结构类似于:

元素0->[hashCode=0,key.value=x1的数据]
元素1->[hashCode=1,key.value=y1的数据]
...
元素n->[hashCode=n,key.value=n1的数据]复制代码

hashMap的put和get方法都会调用hashCode方法,如果两个hashCode有冲突,再调用equals方法:

put():会调用对象的hashCode()方法来计算hashcode,然后找到buchet(桶)位置来储存对象,当获取对象时,通过键对象的equals()方法找到正确的键值对,然后返回值对象。hashMap通过链表来解决冲突问题,如果发生碰撞,对象就会储存在链表的下一节点。

get():buchet(桶)里的第一个节点,直接命中;如果有冲突,则通过key.equals(k)去找对应的可以。

为什么要重写hashCode()和equals():

首先先来看一下equals:

public boolean equals(Object obj){
    return (this==obj);
}复制代码

是通过==来比较两个对象的引用地址,Object的equals只是简单的判断是不是同一个实例,但如果我们需要比较逻辑上的相等,就需要重写equals()方法,而涉及到HashMap的时候,重写了equals()就需要重写hashCode()方法。

2.concurrentHashMap怎么实现

采用了“分段锁”的方式来确保线性安全,相比于HashTable,不会存在锁竞争,可以有效的提高并发效率。

concurrentHashMap的主干是Segment数组

final Segment<K,V>[] segment;复制代码

Segment继承了ReentrantLock,所以它就是一种“可重入锁”。在concurrentHashMap中一个Segment就相当于一个子哈希表,Segment里维护了一个HashEntry数组,在并发情况下,不需要考虑锁的竞争。


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值