这个 equals() 方法 return 怎么会是真的?
How can this equals() method return true?
我正在阅读 Effective Java 中的 equals 合同,在传递部分我遇到了疑问,在下面的代码中:
public class Point {
private final int x;
private final int y;
public Point(int x, int y) {
this.x = x;
this.y = y;
}
现在我们有了这个
@Override
public boolean equals(Object o) {
if (!(o instanceof Point))
return false;
Point p = (Point)o;
return p.x == x && p.y == y;
}
public class ColorPoint extends Point {
private final Color color;
public ColorPoint(int x, int y, Color color) {
super(x, y);
this.color = color;
}
// Remainder omitted
}
// Broken - violates symmetry!
@Override
public boolean equals(Object o) {
if (!(o instanceof ColorPoint))
return false;
return super.equals(o) && ((ColorPoint) o).color == color;
}
ColorPoint cp = new ColorPoint(1, 2, Color.RED);
Point p = new Point(1, 2);
如果我 运行 p.equals(cp) ,它应该 return false 因为
return super.equals(o) && ((ColorPoint) o).color == color;
对两个 class 都无效,因为 point
class 不包含变量 Color
为什么书上写的是真的?
正如您在代码中清楚看到的那样:
ColorPoint cp = new ColorPoint(1, 2, Color.RED);
Point p = new Point(1, 2); // create a Point
p.equals(cp) // call Point::equals
你调用Point::equals()
方法...不比较颜色,想想Point
没有颜色属性.
但是无论如何,您可以使用 cp.equals(p)
:
将两个元素与 ColorPoint::equals
进行比较
ColorPoint cp = new ColorPoint(1, 2, Color.RED);
Point p = new Point(1, 2); // create a Point
System.out.println(p.equals(cp)); // call Point::equals
System.out.println(cp.equals(p)); // call ColorPoint::equals
将输出:
true
false
注意:小心!!!
这个false
不是针对不同的color
属性,是因为p
不是instanceof ColorPoint
!!。
编辑:
thanks a lot , thats bad from my side ..i should have figured it :(
嗯,当你在这种情况下有经验时,更容易理解,但一开始可能很难理解。在这种情况下,遵循我调试的应用程序的流程,但您可以更轻松、更快地实现此信息添加打印语句。
例如:
ColorPoint::equals
@Override
public boolean equals(Object o) {
System.out.println("equals ColorPoint");
if (!(o instanceof ColorPoint))
return false;
return super.equals(o) && ((ColorPoint) o).color == color;
}
Point::equals
@Override
public boolean equals(Object o) {
System.out.println("equals Point");
if (!(o instanceof Point))
return false;
Point p = (Point) o;
return p.x == x && p.y == y;
}
同样的测试程序会输出:
equals Point
true
equals ColorPoint
false
这为您提供了有关正在发生的事情的线索!
我正在阅读 Effective Java 中的 equals 合同,在传递部分我遇到了疑问,在下面的代码中:
public class Point {
private final int x;
private final int y;
public Point(int x, int y) {
this.x = x;
this.y = y;
}
现在我们有了这个
@Override
public boolean equals(Object o) {
if (!(o instanceof Point))
return false;
Point p = (Point)o;
return p.x == x && p.y == y;
}
public class ColorPoint extends Point {
private final Color color;
public ColorPoint(int x, int y, Color color) {
super(x, y);
this.color = color;
}
// Remainder omitted
}
// Broken - violates symmetry!
@Override
public boolean equals(Object o) {
if (!(o instanceof ColorPoint))
return false;
return super.equals(o) && ((ColorPoint) o).color == color;
}
ColorPoint cp = new ColorPoint(1, 2, Color.RED);
Point p = new Point(1, 2);
如果我 运行 p.equals(cp) ,它应该 return false 因为
return super.equals(o) && ((ColorPoint) o).color == color;
对两个 class 都无效,因为 point
class 不包含变量 Color
为什么书上写的是真的?
正如您在代码中清楚看到的那样:
ColorPoint cp = new ColorPoint(1, 2, Color.RED);
Point p = new Point(1, 2); // create a Point
p.equals(cp) // call Point::equals
你调用Point::equals()
方法...不比较颜色,想想Point
没有颜色属性.
但是无论如何,您可以使用 cp.equals(p)
:
ColorPoint::equals
进行比较
ColorPoint cp = new ColorPoint(1, 2, Color.RED);
Point p = new Point(1, 2); // create a Point
System.out.println(p.equals(cp)); // call Point::equals
System.out.println(cp.equals(p)); // call ColorPoint::equals
将输出:
true
false
注意:小心!!!
这个false
不是针对不同的color
属性,是因为p
不是instanceof ColorPoint
!!。
编辑:
thanks a lot , thats bad from my side ..i should have figured it
:(
嗯,当你在这种情况下有经验时,更容易理解,但一开始可能很难理解。在这种情况下,遵循我调试的应用程序的流程,但您可以更轻松、更快地实现此信息添加打印语句。
例如:
ColorPoint::equals
@Override
public boolean equals(Object o) {
System.out.println("equals ColorPoint");
if (!(o instanceof ColorPoint))
return false;
return super.equals(o) && ((ColorPoint) o).color == color;
}
Point::equals
@Override
public boolean equals(Object o) {
System.out.println("equals Point");
if (!(o instanceof Point))
return false;
Point p = (Point) o;
return p.x == x && p.y == y;
}
同样的测试程序会输出:
equals Point
true
equals ColorPoint
false
这为您提供了有关正在发生的事情的线索!