0
点赞
收藏
分享

微信扫一扫

jdk1.8 HashMap哈希表底层采用何种算法计算hash值?如何确定元素在哈希表的下标

关键代码

取hash

自身hashCode 按位异或 hashCode无符号右移16位

当数组的长度很短时,只有低位数的hashcode值能参与运算。而让高16位参与运算可以更好的均匀散列,减少碰撞,进一步降低hash冲突的几率并且使得高16位和低16位的信息都被保留了。

static final int hash(Object key) {
int h;
return (key == null) ? 0 : (h = key.hashCode()) ^ (h >>> 16);
}

元素定位

tab[i = (n - 1) & hash]

重现计算过程

public static void main(String[] args) {

StringBuilder builder = new StringBuilder("在初始容量为16的HashMap中,字符串‘sun’的下标计算过程\n" +
"根据jdk1.8源码,元素hashCode计算方法: hashCode = (h = key.hashCode()) ^ (h >>> 16)\n" +
"元素落在数组的下标 tab[i = (n - 1) & hash])" +
"key.hashCode()=" + "sun".hashCode() + "\n" +
"二进制为:" + Integer.toBinaryString("sun".hashCode()) + "\n" +
"无符号右移16后 " + Integer.toBinaryString(("sun".hashCode()) >>> 16) + "\n" +
"hashCode 按位异或 无符号右移16的结果 " + Integer.toBinaryString(("sun".hashCode() ^ ("sun".hashCode()) >>> 16)) + "\n" +
"与(n-1) 按位 & 后 " + Integer.toBinaryString((15 & ("sun".hashCode() ^ ("sun".hashCode()) >>> 16))) + "\n" +

"转成10进制 " + (15 & ("sun".hashCode() ^ ("sun".hashCode()) >>> 16))

);


System.out.println(builder);
}


举报

相关推荐

0 条评论