最浅层的了解--浅谈HashMap

HashMap可以说是非常经典,不然也不会有那么多面试官问了,嘿嘿,

作为一个不太菜的菜鸟,我今天和大家一起分享下HashMap。

HashMap 简单来说就是一个Map与一个Hash的组合,大家都知道List的底层吧?List的底层就是一个Array,当其中对象超过其容量时,这个Array便会扩容。也就变成了所谓的“不限定长度”的集合List。

可以说,List的这种结果也是HashMap底层的一部分。看过HashMap底层的同学都知道,HashMap是由四个Field组成:hashCode,

Entry<key,value>(算是两个),还有一个next.下面我来给大家简单说下:

1.HashCode,这个大家都知道,Hash值,是通过一种散列算法算出来的,这样说可能有点陌生,大家看下面一段代码,任何一个对象都可以生成一个HashCode 的,然后对这个HashCode 取余,就能获得一个你想要的hash值了,至于为什么取余,嘿嘿,总不可能你第一次创建就创建一个上亿存储量的数组吧,既占内存,影响性能,也没有必要。你创建的HashMap 的所有hashCode其实就是一个Array,当然这个Array到达一定容量的时候也会扩容,也就是说这个hashCode 类似于一个List。

public class HashMaps {

    public static void main(String[] args) {
        Integer random=123;
        int i = random.hashCode()%16;

        String random1 = "125";
        int k = random1.hashCode() % 16;

        System.out.println("hash数值1:"+i+"\n hash数值2:"+k);
    }
}

2、Entry<key,value>,这个Entry想必大家都看出来了,是一个Map,就相当于Map<key,value>。

这里简单给大家说下HashMap 的存储过程,对象存储到HashMap中,第一步,先求出HashCode,然后这个对象就存放到Entry中的key 中了。这就是HashTable 了,如果是hashMap,那就是先找到hashCode,然后把Map<key1,value1>,放到Entry<key,value>当中。我们查询时就能先查询出HashCode,然后找到这个Map了。 

3.next,可能有小伙伴就问,万一你获取的code一样了怎么办?那你查询的时候不是有两个对象了?这不是出事故了吗?不错,确实有这种可能,所以,HashMap中就有了一个next来处理这种问题。

比如连个Map对象map1<"key","我很菜">,map2<"key1","菜鸟也是可以成长滴">,假如map1和map2最终获取的hashCode都是4,map1放到序列之中,带再次添加map2时,HashMap会查询4这个位置是否是null,当然,此时不是空的,于是就查找 ->next,然后判断next是否是空的。之后递归调用,直到查询到一个末尾,然后添加进去,这其实是一个链表。

从下图看,HashMap就是一个表格,先有一列,当某列冲突时,这一列就会横向延伸。

有些同学可能疑惑,创建完成之后这个HashMap不就固定了吗?怎么还能横向纵向延伸?其实,计算机的存储底层都是顺序存储,没有什么二叉树、链表之类的,这些都是一种存储结构,当HashMap分配到一定内存之后,存储方式完全可以按照自己的意愿来处理的。

扩容与性能:

上面刚刚提到,HashMap是顺序存储与链表的结合体,更是集合了顺序存储和链表的优点。但是既然其底层扩容类似List,那么必然有一个初始的长度。这个长度就是容量,这个一般是16,也就是2的4次方,那么什么时候扩容呢?一般是达到容量*负载因子的时候就会扩容,(负载因子=0.75)。大家会发现16的二进制标示是10000,扩容的话是容量*2,也就是32,二进制是100000。大家在可以再看看容量*负载因子的二进制标识。大家仔细观察对比,看看有什么发现,具体的话,下次再说哦~

 

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

笔下天地宽

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值