在TreeSet中执行Comparator后删除元素

时间:2014-10-20 15:17:27

标签: java comparator treeset

我有这种代码的和平:

final SortedSet<NisType> lAllNNisType = new TreeSet<NisType>(new NisTypeComparator());
lAllNisType.addAll(pAllNisType); // where pAllNisType is of type ArrayList<NisType>

那是我的比较器类:

  private class NisTypeComparator implements Comparator<NisType> {

    @Override
    public int compare(NisType pNisType, NisType pNisType2) {
       if (pNisType.getPrio()>pNisType2.getPrio())
         return 1;
       else if (pNisType.getPrio()<pNisType2.getPrio())
         return -1;
       else
         return 0;
    }
  }

My ArrayList pAllNisType填充了6个不同的对象(基于equals和hashCode方法)。 然而,在这条线被执行后:

lAllNisType.addAll(pAllNisType);

lAllNisType仅包含5个对象。 有一个比较返回0.由于这一个对象已从lAllNisType中删除。

我不知道这里发生了什么。 对象是不同的。如果我做那样的事情:

final Set<NisType> lAllNisType = new HashSet<NisType>(pAllNisType);

lAllNisType有6个元素。

感谢您的帮助

的Stefan

1 个答案:

答案 0 :(得分:1)

是的,这表现得与documented.

完全相同
  

请注意,如果有序集合要正确实现Set接口,则由有序集合维护的排序(无论是否提供显式比较器)必须与equals一致。 (有关与equals一致的精确定义,请参阅Comparable接口或Comparator接口。)这是因为Set接口是根据equals操作定义的,但是有序集使用其compareTo执行所有元素比较(或者比较)方法,因此,从排序集的角度来看,这种方法被认为相等的两个元素是等于。即使排序与equals不一致,排序集的行为也是明确定义的;它只是没有遵守Set接口的一般合同。

如果compare返回0,那么就该集合而言,您的两个元素被认为是相等的,并且只有其中一个元素可以出现在集合中。如果要保留两个对象,则需要让比较器区分它们,例如:通过二次订购。