博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
计算hashCode的常见方法
阅读量:6227 次
发布时间:2019-06-21

本文共 1589 字,大约阅读时间需要 5 分钟。

  1. 把某个非零常数值,比如说17,保存在一个叫result的int类型的变量中。

2.对于对象中每一个关键域f(值equals方法中考虑的每一个域),完成以下步骤:

a.为该域计算int类型的散列吗c:

i. 如果该域是boolean类型,则计算

[java] view plain copy

f?0:1

ii. 如果该域是byte、char、short或者int类型,则计算

[java] view plain copy
(int)f

iii.如果该域是long类型,则计算

[java] view plain copy
(int)(f ^ (f >>> 32))

iv. 如果该域是double类型,则计算

[java] view plain copy
Double.doubleToLongBits(f)

得到一个long类型的值,然后按照2.a.iii,对该long型值计算散列值。

vi. 如果该域是一个对象引用,并且该类的equals方法通过递归调用equals的方式来比较这个域,则同样对这个域递归调用hashCode,如果要求一个更为复杂的比较,则为这个域计算一个“规范表示(canonical representation)”,然后针对这个范式调用hashCode。如果这个域为null,则返回0(或者是某个常数,但习惯上使用0)。

vii. 如果该域是一个数组,则把每一个元素当做单独的域处理。也就是说,递归地应用上诉规则,对每一个重要的元素计算散列值,然后根据2.b的方法把这些散列值组合起来。

b.按照下面的公式,把步骤a得到的散列值组合到result中:

[java] view plain copy

result = 37 * result + c;

3.返回result

4.写完了hashCode后,问自己相等的实例具有相同的hashCode么?假如不是,找出原因并修正。

在散列码的计算过程中,把冗余域排除在计算之外是可以接受的。换句话说,如果一个域的值可以根据其他域值计算出来,则把这样的域排除在外是可以接受的。

举例,假如一个类PhoneNumber有三个关键域:areaCode,exchange,extension,都是short类型,则hashCode的计算过程为:

[java] view plain copy

@Override
public int hashCode(){
int result = 17;
result = result * 37 + areaCode;
result = result * 37 + exchange;
result = result * 37 + extension;
return result;
}
如果一个类是可变的,并且计算散列码的代价也比较大,那么你应该考虑把散列码缓存到对象的内部,而不是每次请求的时候都计算散列值。如果你觉得这种类型的大都数值会被用作散列键,那么你应该在实例被创建的时候计算散列值,否则,你可以选择“延迟初始化”散列码,一直到hashCode第一次调用才开始计算。
假如PhoneNumber这样处理,那么代码为:

[java] view plain copy

//延迟初始化
private volatile int hashCode = 0;

@Override

public int hashCode(){
if(hashCode == 0){
int result = 17;
result = result * 37 + areaCode;
result = result * 37 + exchange;
result = result * 37 + extension;
hashCode = result;
}
return hashCode;
}

转载地址:http://eknna.baihongyu.com/

你可能感兴趣的文章
js随机背景颜色
查看>>
NTFS文件系统简介
查看>>
[IOC]Unity使用
查看>>
PUTTY的使用教程
查看>>
永远的经典-意大利波伦塔蛋糕Polenta Cake
查看>>
[转载] C#面向对象设计模式纵横谈——22 State状态模式
查看>>
HDOJ_ACM_Max Sum
查看>>
LeetCode 141, 142. Linked List Cycle I+II
查看>>
管道函数
查看>>
14.多线程设计模式 - Master-Worker模式
查看>>
机器学习实战——k-近邻算法
查看>>
设计模式——单例模式
查看>>
240. Search a 2D Matrix II
查看>>
php-预定义
查看>>
IntelliTrace 调试、定位异常
查看>>
linux Shell脚本编码格式
查看>>
String方法
查看>>
冲刺第五天
查看>>
php操作mysql与sqlite类
查看>>
Bitmap压缩到指定尺寸大小,获取圆角、圆形图片
查看>>