HashMap面试题

HashMap

1.HashMap的底层结构是什么?

● 在JDK1.7中,底层数据结构是数组+链表
● 在JDK1.8中,底层数据结构是数组+链表+红黑树

2.JDK1.8中什么情况下,链表会转变为红黑树?

● 当数组长度大于64且链表节点个数大于8时才会转变为红黑树,如果链表节点个数小于6则又会退化为链表
● 在链表转换为红黑树前面会进行判断,如果数组长度小于64,则会优先选择扩容。

3.为什么在解决 hash 冲突的时候,不直接用红黑树?而选择先用链表,再转红黑树?

● 因为红黑树需要进行左旋,右旋,变色这些操作来维持平衡,而单链表不需要,当元素小于8个的时候,此时查询操作,链表结构已经可以保证性能。当元素大于8个的时候,红黑树搜索事件负责度是0(logn),而链表是O(n),此时需要红黑树来加快查询速度,但是新增节点的效率变慢了

4.为什么用红黑树,不要二叉查找树

● 因为二叉查找树在极端条件下会变成线性结构,也就是链表,时间负责度没有改变

5.为什么链表转红黑树的阈值是8

● 因为泊松分布,作者在注释里面写了:按照泊松分布的计算公式计算出了桶中元素个数和概率的对照表,可以看到链表中元素个数为 8 时的概率已经非常小,再多的就更少了,所以原作者在选择链表元素个数时选择了 8,是根据概率统计而选择的

6.默认加载因子是多少?为什么是 0.75,不是 0.6 或者 0.8 ?

● 默认的loadFactor是0.75,0.75是对空间和时间效率的一个平衡选择。

7.为什么 hash 值要与length-1相与?

● 把 hash 值对数组长度取模运算,模运算的消耗很大,没有位运算快。
● 当 length 总是 2 的n次方时,h& (length-1) 运算等价于对length取模,也就是 h%length,但是 & 比 % 具有更高的效率。

8.hash冲突的解决方法

比较出名的有四种(1)开放定址法(2)链地址法(3)再哈希法(4)公共溢出区域法

9.我用LinkedList代替数组结构可以么?

可以但是没有必要,因为用数组效率最高! 在HashMap中,定位桶的位置是利用元素的key的哈希值对数组长度取模得到。此时,我们已得到桶的位置。显然数组的查找效率比LinkedList大。

10.我用ArrayList可以吗,ArrayList底层也是数组?

因为采用基本数组结构,扩容机制可以自己定义,HashMap中数组扩容刚好是2的次幂,在做取模运算的效率高。 而ArrayList的扩容机制是1.5倍扩容。

11.HashMap在什么条件下扩容

如果元素节点个数超过了loadfactorcurrent capacity,就要resize。加载因子数组大小。

12.说说String中hashcode的实现?

public int hashCode() {
int h = hash;
if (h == 0 && value.length > 0) {
char val[] = value;

    for (int i = 0; i < value.length; i++) {
        h = 31 * h + val[i];
    }
    hash = h;
}
return h;

}
以31为权,每一位为字符的ASCII值进行运算,用自然溢出来等效取模。
哈希计算公式可以计为 s[0]31^(n-1) + s[1]31^(n-2) + … + s[n-1]
那为什么以31为质数呢?
主要是因为31是一个奇质数,所以31
i=32
i-i=(i<<5)-i,这种位移与减法结合的计算相比一般的运算快很多。

参考:https://zhuanlan.zhihu.com/p/76735726

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值