hashcode() equals()

一、定义
hashcodes不等 equals必定不等;
equals相等,hashcodes必定相等。
二、原因
hashcodes是为了hash表使用的。

假想:如果一个不允许元素重复(HashSet),那么怎么确定将要添加的元素集合中不存在?

1、错误做法,每个对象去equals一下,虽然可以达到效果,但是却不可采用,如果集合中已经存在几万个元素,那么就得euqals几万遍,太闹心了,花费时间不允许;

2、正确做法,先比较每个对象hashcodes方法,如果相同,再进行equals比较。

三、如何重写
1、hashcode()
       Google首席Java架构师Joshua Bloch在他的著作《Effective Java》中提出了一种简单通用的hashCode算法

        1. 初始化一个整形变量,为此变量赋予一个非零的常数值,比如int result = 17;

        2. 选取equals方法中用于比较的所有域,然后针对每个域的属性进行计算:
    
              (1) 如果是boolean值,则计算f ? 1:0
        
              (2) 如果是byte\char\short\int,则计算(int)f
            
              (3) 如果是long值,则计算(int)(f ^ (f >>> 32))
            
              (4) 如果是float值,则计算Float.floatToIntBits(f)
            
              (5) 如果是double值,则计算Double.doubleToLongBits(f),然后返回的结果是long,再用规则(3)去处理long,得到int
            
              (6)如果是对象应用,如果equals方法中采取递归调用的比较方式,那么hashCode中同样采取递归调用hashCode的方式。否则需要为这个域计算一个范式,比如当这个域的值为null的时候,那么hashCode值为0
            
              (7)如果是数组,那么需要为每个元素当做单独的域来处理。如果你使用的是1.5及以上版本的JDK,那么没必要自己去重新遍历一遍数组,java.util.Arrays.hashCode方法包含了8种基本类型数组和引用数组的hashCode计算,算法同上。

            
            @Override  
            public int hashCode() {  
              int result = 17;  
              result = result * 31 + name.hashCode();  
              result = result * 31 + age;  
        
              return result;  
            }  

            备注     31可以 由i*31== (i<<5)-1来表示,使用31的原因可能是为了更好的分配hash地址,并且31只占用5bits! 

            
2、重写euqals()
    
    @Override 
    public boolean equals(Object obj) { 
         if(this == obj)
             return true; 
         if(obj == null)
                return false; 
         if (!(obj instanceof User)) { 
             return false; 
         } 
         MyClass o = (MyClass)obj; 
         return '对象中每个属性比较'; 
    }
参考:https://blog.csdn.net/zhengchao1991/article/details/78916471 

 

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值