2012-07-11 136 views
3

可能重复:
Java: Array of primitive data types does not autobox为什么autoboxing在这种情况下不适用于泛型?

我最近一直在做一些Java(主要是因为什么我在大学里为我现在的工作做了回顾不涉及任何Java在所有),而一件从未正确介绍给我们的东西是泛型。

我已经做了甲骨文的Java网站上的泛型教程,我一直在用下面的例子难倒我修改了一下:

public static <Integer extends Comparable<Integer>> int countGreaterThan(Integer [] anArray, Integer elem) { 
    int count = 0; 
    for (Integer e : anArray) 
     if (e.compareTo(elem) > 0) 
      ++count; 
     return count; 
} 

而且我用这个方法来比较整数数组用下面的整数:

Integer [] numarr = {1, 2, 3, 4 , 5}; 
Integer num = new Integer(5); 

int count = Util.countGreaterThan(arrnum, num); 

这似乎是工作正常,但是如果我通过一个基本数组和原始INT,它不会:

int [] arrnum = {1, 2, 3, 4 , 5}; 
int othernum = 3; 

int count = Util.countGreaterThan(arrnum, othernum); 

编译器会抱怨有:

method countGreaterThan in class Generics.Util 
cannot be applied to given types; 
required: Integer[],Integer 
found: int[],int 
reason: no instance(s) of type variable(s) 
Integer exist so that argument type int conforms to formal parameter type Integer 

的教程似乎是很固执的认为Java将永远autobox /拆箱的对象和原语为必要,但它不会做,在这种特殊情况下,我是什么失踪?

另外什么可能是一种很好的方式来尽可能地概括这种比较方法?如果我使用T而不是Integer,那么它会查找T对象,而不是我传递给它的任何东西。

我很抱歉,如果这篇文章令人困惑,并且我对上面提到的东西看起来很无知,那只是我一直主要作为perl程序员(而且并不是特别有经验的程序员)并在那里概括似乎不是一个问题(由于缺乏类型强制执行)。

在此先感谢!

+0

使用'Integer'作为一个类型变量是一个非常糟糕的主意 – newacct 2012-07-11 18:08:35

回答

1

下面的代码似乎就我所看到的工作:

public static <Integer extends Comparable<Integer>> int countGreaterThan(Integer [] anArray, Integer elem) { 
    int count = 0; 
    for (Integer e : anArray) { 
     if (e.compareTo(elem) > 0) 
      ++count; 
     return count; 
} 

虽然我得到一个警告"The type parameter Integer is hiding the type Integer"。请参阅@ErichSchreiner的答案,以解释为什么自动装箱在这里不起作用。

你的方法的一个很好的概括是:

public static <T extends Comparable<? super T>> int countGreaterThan(T[] anArray, T elem) { 
    int count = 0; 
    for (T e : anArray) { 
     if (e.compareTo(elem) > 0) { 
      ++count; 
     } 
    } 
    return count; 
} 

你真正关心的是anArray具有相同类型的元素作为elem是,和它媲美它自己的类型。

+0

你打我... :-) – 2012-07-11 08:29:20

+0

虽然你做了一个更好的解释自动装箱问题,增加了一个参考。 – Keppil 2012-07-11 08:32:46

+0

为获得最佳效果,请使用'>' – newacct 2012-07-11 18:09:23

1

您的声明countGreaterThan()隐藏内置类型Integer。为了澄清,考虑稍作修改的版本:

public static <I extends Comparable<I>> int countGreaterThan(I [] anArray, I elem) { 
    int count = 0; 
    for (I e : anArray) 
     if (e.compareTo(elem) > 0) 
      ++count; 
     return count; 
} 

现在应该很明显,你在呼唤第二次尝试不能工作,因为就没有自动装箱完成。要使泛型能够工作,您需要提供对象,而不是基元。

+0

啊哈,谢谢!我认为既然我可以用一个Integer返回类型声明一个普通的方法,然后传递一个原语给它,没有任何问题,我可以在泛型中做同样的事情。 我也尝试将一个泛型类传递给count方法(沿着'public class Box '行),但是失败: 'required:T [],T found:泛型。盒[],Generics.Box 原因:推断类型不符合宣告约束(S) ' 它是安全的假设,我无法通过泛型类的countGreaterThan(与作为签名)要么? 谢谢! @Keppil – Nobilis 2012-07-11 08:54:16

相关问题