比较方法违反了Java 7中的一般合同

在Java 7中编译一些Java代码然后运行它之后,我得到了一个“比较方法违反了它的一般合同”。

我看过比较方法违反了它的总合同! 仅限Java 7并意识到我的代码在以前版本的Java中被忽略了。 但是,我无法弄清楚我的代码有什么问题。 Collections.sort()生成错误。

我的代码是:

public Comparator sortBySmoothDays() { Comparator c = new Comparator() { public int compare(Object arg0, Object arg1) { Date date0 = ((PosObject)arg0).getDate(); Date date1 = ((PosObject)arg1).getDate(); double d1 = MyUtils.calcSmoothDays(date0, new Date()); double d2 = MyUtils.calcSmoothDays(date1, new Date()); if (d1 >= d2) { return 1; } else { return -1; } } }; return c; } Comparator c = ComparatorUtils.getInstance().sortBySmoothDays(); Collections.sort(posList, c); 

有人可以帮忙吗? 谢谢!

如果值相等,比较器必须返回0。 在当前的实现中,如果它们相等则返回1。 正确比较double值的最简单方法是调用Double.compare

 double d1 = MyUtils.calcSmoothDays(date0, new Date()); double d2 = MyUtils.calcSmoothDays(date1, new Date()); return Double.compare(d1, d2); 

使用比较器,每个对象都比自身更大: compare(x,x)总是返回一个。

这违反了以下要求 :

实现者必须确保所有x和y的sgn(compare(x,y))== -sgn(compare(y,x))。

上述要求意味着compare(x,x)必须返回零。

我建议阅读合同并确保您的实施符合要求。

特别是,如果是date0.equals(date1) ,比较器可能应该立即返回零,而不进行任何浮点转换和比较。

问题是如果两个对象比较相等,即calcSmoothDays返回相同的值,那么你可能会遇到compare(object1,object2)== 1和compare(object2,object1)== 1的情况?

所以它意味着object1> object 2和object2> object 1 …