如何在Java中对泛型类型列表进行排序

时间:2013-01-29 07:39:57

标签: java generics sorting

我有一组所有共享一些共同属性的类,因此我将它们都扩展为一个公共基类BaseEntity。我有,例如Foo extends BaseEntityBar extends BaseEntity

我还希望这些FooBar对象的列表可以排序,因此我实现了Comparable。我将类定义为Foo extends BaseEntity implements Comparable<Foo>Bar extends BaseEntity implements Comparable<Bar>,并且FooBar列表的排序按预期工作 - 当然还有排序的详细信息在不同的子类中是不同的。但是,当我事先不知道我是否会FooBar时,我无法解决如何进行分类工作的问题。例如,此代码无法编译:

public class UtilityClass<T extends BaseEntity> {

  ...bunch of stuff...

  List<T> values;

  public List<T> sort() {
    Collections.sort(values);
    return values;
  }

  ...more methods...
}

错误消息Bound mismatch: The generic method sort(List<T>) of type Collections is not applicable for the arguments (List<T>). The inferred type T is not a valid substitute for the bounded parameter <T extends Comparable<? super T>>

我认为问题在于我正在尝试对BaseEntity个对象进行排序,而BaseEntity本身并未实现Comparable。但是现在我遇到了一个问题:使BaseEntity个对象与其他BaseEntity个对象相比是唯一合理的事情,但是当我将implements Comparable<BaseEntity>添加到BaseEntity时,编译器会告诉我我现在遇到问题,因为我的Foo课程正在尝试实施Comparable<BaseEntity>Comparable<Foo>,这显然是不允许的。

我知道我可以通过放弃implements Comparable<Foo>而只是实施Comparable<BaseEntity>来回避这个问题,但是我的compareTo方法将不得不进行丑陋的投射,我认为这正是使用泛型的一些问题应该避免。

我真正想要做的是在BaseEntity的签名中指定其所有子类都是Comparable,但仅限于同一子类的实例。

感激地收到任何帮助。谢谢!

4 个答案:

答案 0 :(得分:7)

使用交叉类型,如下所示:

public class MyList<T extends BaseEntity & Comparable<T>> {...}

指定T必须同时为BaseEntity Comparable

答案 1 :(得分:2)

不要使用Collections.sort(List<T>),而是使用Collections.sort(Lst<T>, Comparator<? extends T>)。将比较代码写入比较器。

答案 2 :(得分:0)

试试这个:

static <T extends Comparable<? super T>> sort(T[] array);

这是完成任务的最通用规范。基本上,它声称,T是一种可以与自身进行比较的类型。

答案 3 :(得分:0)

您可以创建一个超级简单的排序方法,该方法几乎可以处理任何列表类型

public class Tools {

    public static <E> void sortList(List<E> list, Comparator<E> comparator) {
        Collections.sort(list, comparator); 
    }

    // Any other utility methods/resources you want in here

}

这意味着只要给定的List和Comparator的类型相同,就可以调用此方法对任何List进行排序。即使没有您的基类(BaseEntity),它也可以工作