Boa*_*ann 7 java equals complex-numbers
我在Java中创建一个复杂的数字类,如下所示:
public class Complex {
public final double real, imag;
public Complex(double real, double imag) {
this.real = real;
this.imag = imag;
}
... methods for arithmetic follow ...
}
Run Code Online (Sandbox Code Playgroud)
我实现了这样的equals方法:
@Override
public boolean equals(Object obj) {
if (obj instanceof Complex) {
Complex other = (Complex)obj;
return (
this.real == other.real &&
this.imag == other.imag
);
}
return false;
}
Run Code Online (Sandbox Code Playgroud)
但是如果你重写equals,你也应该覆盖hashCode.其中一条规则是:
如果两个对象根据equals(Object)方法相等,则对两个对象中的每一个调用hashCode方法必须生成相同的整数结果.
比较floats和doubles进行==数值比较,因此+0.0 == -0.0NaN值不等于包括它们在内的所有东西.所以我尝试实现hashCode方法来匹配equals方法,如下所示:
@Override
public int hashCode() {
long real = Double.doubleToLongBits(this.real); // harmonize NaN bit patterns
long imag = Double.doubleToLongBits(this.imag);
if (real == 1L << 63) real = 0; // convert -0.0 to +0.0
if (imag == 1L << 63) imag = 0;
long h = real ^ imag;
return (int)h ^ (int)(h >>> 32);
}
Run Code Online (Sandbox Code Playgroud)
但后来我意识到如果任何一个字段是NaN,这在哈希映射中会奇怪地工作,因为它this.equals(this)总是假的,但也许这不是错误的.另一方面,我可以做什么Double,Float做什么,等于方法比较+0.0 != -0.0,但仍然协调不同的NaN位模式,然后让NaN == NaN,所以然后我得到:
@Override
public boolean equals(Object obj) {
if (obj instanceof Complex) {
Complex other = (Complex)obj;
return (
Double.doubleToLongBits(this.real) ==
Double.doubleToLongBits(other.real) &&
Double.doubleToLongBits(this.imag) ==
Double.doubleToLongBits(other.imag)
);
}
return false;
}
@Override
public int hashCode() {
long h = (
Double.doubleToLongBits(real) +
Double.doubleToLongBits(imag)
);
return (int)h ^ (int)(h >>> 32);
}
Run Code Online (Sandbox Code Playgroud)
但如果我这样做,那么我的复数就不像实数那样+0.0 == -0.0.但我真的不需要将我的复杂数字放在哈希映射中 - 我只是想做正确的事情,遵循最佳实践等等.现在我只是感到困惑.有人可以告诉我最好的方法吗?
病态的情况似乎是这样0.0 != -0.0,所以我会确保这种情况永远不会发生,并完全按照 Joshua Bloch 在“Effective Java”中告诉您的方式完成其余的工作。
| 归档时间: |
|
| 查看次数: |
3036 次 |
| 最近记录: |