比较方法违反了其总合同

时间:2016-02-08 07:05:04

标签: java

我试图对列表进行排序。我使用了Collections.sort(list),我得到了一个IllegalArgumentException异常 我知道这适用于jdk6,而jdk7正在使用TimSort。我得到的规则如下。我认为我做对了,但它没有用。

有没有人可以给我一个我的代码不起作用的情况?非常感谢

规则:

> 1.sgn(compare(x, y)) == -sgn(compare(y, x))
> 
> 2.((compare(x, y)>0) && (compare(y, z)>0)) implies compare(x, z)>0
> 
> 3.compare(x, y)==0 implies that sgn(compare(x, z))==sgn(compare(y, z)) for all z





//StringUtil.isBlank(str) return if str==null||str.trim().length()==0
@Override
public int compareTo(NovelChapter o) {
    if(o == null){
        return 1;
    }
    else if(o.equals(this) || this == o){
        return 0;
    }

    if(!StringUtil.isBlank(o.getSourceUrl())&& !StringUtil.isBlank(this.getSourceUrl())){
        if(o.getSourceUrl().length() != this.getSourceUrl().length()){
            return o.getSourceUrl().compareTo(this.getSourceUrl());
        }
        else{
            return o.getSourceUrl().compareTo(this.getSourceUrl()) * (-1);
        }
    }
    else if(!StringUtil.isBlank(o.getSourceUrl())&& !StringUtil.isBlank(this.getSourceUrl())){
        return 1;
    }
    else if(!StringUtil.isBlank(o.getSourceUrl())&& StringUtil.isBlank(this.getSourceUrl())){
        return -1;
    }
    else{
        return 0;
    }
}

BTW,System.setProperty("java.util.Arrays.useLegacyMergeSort", "true");正在使用jdk6,它本身并没有解决问题。

=============================================== =

感谢所有的答案,我改变了代码,现在它抛出NPE。现在它更好吗?但它仍然给我相同的例外。

@Override
public int compareTo(NovelChapter o) {

    if(o == null){
        throw new NullPointerException();
    }else if(o.equals(this) || this == o){
        return 0;
    }

    String self = this.getSourceUrl();
    String item = o.getSourceUrl();

    if(self == null && item != null){
        return -1;
    }else if (self == null && item != null){
        return 1;
    }else if(self == null && item == null){
        return 0;
    }

    if(self.length() == item.length()){
        return self.compareTo(item);
    }else{
        return self.compareTo(item) * (-1);
    }

}

2 个答案:

答案 0 :(得分:1)

我无法看到该异常的具体原因,但您向我们展示的代码中存在一些问题。

  1. 不应在compareTo上使用null方法,因此您对null的特殊处理不应该存在。比较器>应该<<抛出NPE。 (并且推论是您不应该尝试对包含null值的数组/集合进行排序。)

  2. 您对trim的使用看起来不一致。当你寻找"空白"网址,但不是在比较"非空白"网址。怪异。

  3. 我想补充一点,你的代码是冗长而低效的。您不应该在if / else语句链中重复调用isBlank实用程序,而应该将两个URL转换为可以直接比较的字符串(我猜测)。

    最后,您必须拥有isBlank方法这一事实说(对我而言)其余代码在维护数据一致性方面做得很差。应该只有一个表示意味着"没有源URL" ......不(至少)三个。

    这个问题有很多可能的原因,只能通过检查所涉及的完整类来消除......从NovelChapter开始,以及getSourceUrl()返回的任何内容。

答案 1 :(得分:0)

来自Comparable Javadoc:

  

请注意,null不是任何类的实例,而e.compareTo(null)   即使e.equals(null)返回,也应抛出NullPointerException   假的。