您的位置 首页 java

一篇文章让你彻底学会重写equals方法

下文笔者讲述 Java 中重写equals方法的相关简介及说明,如下所示

equals方法简介

 在java的顶级基类中有一个对象Object类拥有一个方法equals
equals方法的功能:
    用于比较两个对象是否完全相等,当两个对象完全相等时,则返回true
  

Object类中equals方法的源码

 java中,Object类中有一个equals方法:

public boolean equals(Object obj) {
    return (this == obj);
}
从以上代码中,我们可以看出Object中的equals方法
对比的为两个对象的引用地址
  
 注意事项:
    在一些自定义对象中,我们通常会重写equals方法
并采用自身定义的对象是否相同的界定规则
  

重写equals方法注意事项

 覆盖equals方法须遵循
     自反性 (reflexive)
    对称性(symmetric)
传递性(transitive)
一致性(consistent)
非null对象与null进行equals比较必为false等约定。

自反性:a!=null,则a.equals(a)返回true.
对称性:a!=null,b!=null,则a.equals(b) == b.equals(a).
传递性:a!=null,b!=null,c!=null,如果a.equals(b) == b.equals(c),这a.equals(c).
一致性:a!=null,b!=null,如果a,b没有被修改,那么不管调用多少次equals,返回的结果始终只有一个.
非null对象与null进行equals比较必为false.
  

重写equals方法的步骤

 使用“==”操作符检查参数是否是这个对象的引用。
检查参数是否为空。
检查参数类型是否匹配。
把参数转换为正确的类型。
对于类中需要进行逻辑判断的属性,检查参数的属性是否与这个对象的属性相同(比较属性也使用对于属性所属类型的equals方法)。
编写完成后,验证是否满足对称、传递、一致等特性。
写equals方法需要注意的地方
覆盖equals时总要覆盖 hashCode 方法,避免一些预想不到的错误。
不要将equals声明中的Object对象替换为其他类型,因为参数不同的相同方法名是重载而不是重写,这可能让程序运行结果变得难以预料。
  

例:
重写一个User对象中的equals方法
当用户名和手机号都相同时候,则认为两个对象是同一个用户
此时我们需重写equals和hashCode
并遵循自反、对称、传递、一致、null比较等测试

 package com.java265;

public class User {
    /** 用户名 */     private  String name;
    /** 手机号 */    private String phone;
    public User(String name, String phone) {
        super();
        this.name = name;
        this.phone = phone;
    }
    public String getName() {
        return name;
    }
    public  void  setName(String name) {
        this.name = name;
    }
    public String getPhone() {
        return phone;
    }
    public void setPhone(String phone) {
        this.phone = phone;
    }
    @Override
    public int hashCode() {
        final int prime = 31;
        int result = 1;
        result = prime * result + ((name == null) ? 0 : name.hashCode());
        result = prime * result + ((phone == null) ? 0 : phone.hashCode());
        return result;
    }
    @Override
    public boolean equals(Object obj) {
        //1.使用“==”操作符检查参数是否是这个对象的引用
        if (this == obj){
            return true;
        }
        //2.检查参数是否为空
        if (obj == null){
            return false;
        }
        //3.检查参数类型是否匹配
        if (getClass() != obj.getClass())
            return false;
        //4.把参数转换为正确的类型
        User other = (User) obj;
        //5.对于类中需要进行逻辑判断的属性,检查参数的属性是否与这个对象的属性相同
        if (name == null) {
            if (other.name != null)
                return false;
        } else if (!name.equals(other.name))
            return false;
        if (phone == null) {
            if (other.phone != null)
                return false;
        } else if (!phone.equals(other.phone))
            return false;
        return true;
    }
    public  static  void main(String[] args) {
        System.out.println("test begin");
        User a = new User("a", "139xxxxxxxx");
        User b = new User("a", "139xxxxxxxx");
        User c = new User("a", "139xxxxxxxx");
        //自反性
        assert a.equals(a);
        //传递性
        assert a.equals(b) == b.equals(c) ? a.equals(c) : false;
        //对称性
         boolean  result = a.equals(b);
        assert result == b.equals(a);
        //一致性 
        for(int i = 0; i < 66; i++){
            assert result == a.equals(b);
        }
        //非null对象与null进行equals比较必为false
        assert a.equals(null) == false;
        System.out.println("test end");
        assert false;
    }
}

注意事项:
    代码启动时,需在 JVM 中加上 -ea选项 开启断言   

文章来源:智云一二三科技

文章标题:一篇文章让你彻底学会重写equals方法

文章地址:https://www.zhihuclub.com/170140.shtml

关于作者: 智云科技

热门文章

网站地图