浅谈equals

浅谈equals

== 比较的是运行时常量池中两个元素的值。对于基本数据类型是,值就是内容本身,因此只要内容一样,==的结果就是true。对于引用数据类型,运行时常量池中存储的是其地址值,因此,即使是两个元素内容一样,但是地址不一样的话,==的值就会是false.

  1. Object中的equals

    public boolean equals(Object obj) {  
    return (this == obj);  
    }
    

    Object中的equals很简单,使用==进行比较,比较的是地址。

  2. String中的equals

    public boolean equals(Object anObject) {  
        if (this == anObject) {  
            return true;    //地址值相等,一定为true
        }  
        return (anObject instanceof String aString)  //判断是否是同一类型
                && (!COMPACT_STRINGS || this.coder == aString.coder)  
                && StringLatin1.equals(value, aString.value);  
    }
    

    代码使用instanceof操作符来判断anObject是否是String类型的实例,即判断anObject是否也是一个字符串对象。如果anObject不为String类型的实例,或者为null,那么直接返回false,因为一个字符串对象不可能与非字符串对象相等。代码调用StringLatin1.equals方法,该方法是一个静态方法,用于比较两个字符串的内容是否相等。如果内容相同,则返回true,否则返回false

    StringLatin1.equals方法:

    public static boolean equals(byte[] value, byte[] other) {  
        if (value.length == other.length) {  
            for (int i = 0; i < value.length; i++) {  
                if (value[i] != other[i]) {  
                    return false;  
                }  
            }  
            return true;  
        }  
        return false;  
    }
    

    可以看到该代码是直接遍历字符串,将其中的值取出来比较。比较的是内容。

  3. Arrays中的equals

    public static boolean equals(long[] a, long[] a2) {  
        if (a==a2)  
            return true;  
        if (a==null || a2==null)  
            return false;  
      
        int length = a.length;  
        if (a2.length != length)  
            return false;  
      
        return ArraysSupport.mismatch(a, a2, length) < 0;   
    }
    
  4. 重写equals

    为什么要重写equals方法?

    前面已经提到,Object中的equals是直接使用==来进行比较,对于引用数据类型,这是比较的地址值。当我们使用String或者Arrays时,这些类已经为我们提前重写了equals方法使得我们可以比较对象的内容。可是对于我们自定义的类呢?如果我们不重写equals方法,在使用equals时则是默认调用Object中的equals方法 ( 毕竟Object是所有类的祖宗 ) ,而这个equals并不是我们想要的。因此,我们需要重写equals方法。

    public class Person {  
        private String name;  
        private int age;  
      
        //无参构造  
        public Person() {  
      
        }  
      
        public Person(String name, int age) {  
            this.name = name;  
            this.age = age;  
        }  
      
        public String getName() {  
            return name;  
        }  
      
        public int getAge() {  
            return age;  
        }  
      
        @Override  
        public String toString() {  
            return "Person{" +  
                    "name='" + name + '\'' +  
                    ", age=" + age +  
                    '}';  
        }  
      
        //重写equals方法  
        @Override  
        public boolean equals(Object obj) {  
            //判断内存地址  
            if (obj == this) {  
                return true;  
            }  
            if (obj == null) {  
                return false;  
            }  
            //判断是否是同一类型的对象  
            if (obj instanceof Person) {  
                //强制转换成Person类型  
                Person per = (Person) obj;  
                //判断他们的属性值    
                if (this.name.equals(per.name) && this.age == (per.age)) {  
                    return true;  
                }  
            }  
            return false;  
        }  
    }
    

    在以上例子中,创建了一个Person类,该类有两个属性,分别是String类型的nameint类型的age。如果要比较两个人信息是否相等,就需要重写equals。在重写方法中,首先判断两个对象的内存地址相同,如果连地址都相同,就代表他们是同一个对象,那么内容一定相同,因此返回true。接着判断比较的对象是否为空,如果为空,则比较无意义,返回false,二者不相等。接着,如果两个对象内存地址不同,并且都不为空,那么开始判断二者是否是同一类型,如果不是同一类型,也是没有比较的必要了。直接返回false。如果是同一类型,为了让Object能够调用Person的成员变量和成员方法,这样就可以进行内容比较,所以向下转型。之后就开始判断他们的内容咯,内容就是姓名和年龄嘛。这里因为姓名是String类型的,我们可以使用JAVA开发者们已经提前帮我们写好了的String类下的equals来比较内容。又因为ageint类型,这是一个基本数据类型,所以直接用==来比较内容。当二者内容都相等时,就代表我们的目的达成了,这两个对象内容相同,返回true。至此,我们重写了自定义Person类下的equals方法,使其能完成比较两个Person类对象是否内容相同的功能。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值