3.5 equals()
3.5 Equality in ADT and OOP
等价性equals()和==
1、== 引用等价性
- == 对基本数据类型,使用==判定相等
- 如果用==,是在判断两个对象身份标识 ID是否相等(指向内存里的同一段空间)
2、equals() 对象等价性
- 在自定义ADT时,需要重写Object的equals()
- 对对象类型,使用equals()
Equality of immutable types 的重写override 和 重载overload
首先,在Object中实现的缺省equals()是在判断引用等价性,通常不是程序员所期望的
所以需要重写,有两种方式
1、overload
直接使用这个equal()来实现下面的代码会出错
这样进行改进
2、Override
参数类型仍未Object,所以这是override
意义在于先判断thatObject是否为Duration的类型,然后再将其转成Duration的引用,再将转换后的引用对象调用方法和其进行比较。
equals()的自反、传递、对称
hashCode()
1、两个被认为equal的对象hashcode应该相同;
override equal()必须重写hashcode
2、unequal的对象hashcode不能相同
3、Hash code must not change unless object mutated
继续以上例为例
可变对象的观察等价性、行为等价性
观察等价性:在不改变状态的情况下,两个mutable对象是否看起来一致
行为等价性:调用对象的任何方法都展示出一致的结果
对可变类型,实现行为等价性即可。也就是说,只有指向同样内存空间的objects,才是相等的。
所以对可变类型来说,无需重写这两个函数,直接继承Object对象的两个方法即可。
如果一定要判断两个可变对象看起来是否一致,最好定义一个新的方法。
可变不可变对equals()和hashcode()的比较
不可变 |
可变 |
equals()实现行为等价性 |
equals()在实现引用等价性==的基础上实现行为等价性 |
hashcode()把abstrract value映射成一个整数 |
hashcode()把引用映射成一个整数 |
equals()改变必须重写hashcode() |
equals()改变无需重写hashcode() |