问题<T延伸可比较>

我有一个三类:1.class Algorithm ,其中max()Collection找到最大值:

 public class Algorithm { public static <T extends Comparable> T max(Collection coll) { T max = coll.iterator().next(); for (T elm : coll) { if (max.compareTo(elm) < 0) max = elm; } return max; } } 

2.Class Fruit

 public class Fruit implements Comparable { private String name; private int size; public Fruit(String name, int size) { this.name = name; this.size = size; } public int compareTo(Fruit that) { if (size < that.size) return -1; else if (size == that.size) return 0; else return 1; } } 

3.class Apple扩展Fruit

 public class Apple extends Fruit { public Apple(int size) { super("Apple", size); } } 

现在的问题是:

 public class Main { public static void main(String[] args) { Apple a1 = new Apple(10); Apple a2 = new Apple(34); List apples = Arrays.asList(a1, a2); System.out.println(Collections.max(apples).size); } } 

根据这篇文章Java – 语法问题:我应该用这种方式编写它: public static <T extends Comparable> T max(Collection coll) public static <T extends Comparable> T max(Collection coll) 。 但现在工作正常。为什么? Apple类没有实现Comparable并且没有super

[UPDATE]
Java Generics and Collections Book说:

如果没有super通配符,找到List的最大值将是非法的,即使允许查找List的最大值。

假设我们将max方法更改为:

 > T max(Collection coll) 

你无法获得Listmax ,因为Apple没有实现Comparable ,它实现了Comparable 。 但是你和我完全清楚, Apple知道如何将自己与另一个Fruit进行比较,因为它inheritance了这个function。

我们通过将max的声明更改为此来解决问题:

 > T max(Collection coll) 

这意味着我们接受任何T类,以便:

  1. T implements Comparable或者……
  2. T implements Comparable为某些X T implements Comparable ,这样X就是T的超类

为了找到max ,我们必须确保T任何实例都可以安全地接受另一个T实例作为其compare方法的参数。

在第一个场景中,很明显T任何实例都可以安全地接受T另一个实例作为其compare(T)方法的参数。

在第二种情况下, T任何实例都可以安全地接受另一个T实例作为其compare(X)方法的参数,因为T所有实例也是X实例。

您的示例说明了第二种情况,其中T对应AppleX对应Fruit

您使用Collections.max(apples)而不是Algorithm.max

Collections.max声明略有不同:

 public static > T max(Collection coll) 

很抱歉把它带回去,但我认为这很重要。 从Collections.max()更改为Algorithm.max()时,您的代码是否已停止正常工作? 我在jdk8中做了一个类似的测试,我不明白它为什么工作正常,而根据Java Generics和Collections它不应该。

我有一个Fruit抽象类(实现Comparable):

 public abstract class Fruit implements Comparable { private String name; private int size; public Fruit(String name, int size) { this.name = name; this.size = size; } public int compareTo(Fruit that) { if (size < that.size) return -1; else if (size == that.size) return 0; else return 1; } } 

然后我有一个Apple扩展Fruit类:

 public class Apple extends Fruit { public Apple(String name, int size) { super(name, size); } } 

最后:

  public class GenericsTest { @Test public void test1() { final Apple a1 = new Apple("apple1", 50); final Apple a2 = new Apple("apple2", 70); final Apple a3 = new Apple("apple3", 34); final List apples = Lists.newArrayList(a1, a2, a3); System.out.println(GenericsTest.max(apples).getSize()); } private static > T max(Collection coll) { T max = coll.iterator().next(); for (T elm : coll) { if (max.compareTo(elm) < 0) max = elm; } return max; } } 

代码工作,而没有? max方法签名中的super T和List属于Apple类型。 根据你提到的报价,它应该不起作用。 我好像在这里感到困惑......