我想比较一下类型为Comparable的less方法中的两个参数。但是,如果我使用comapreTo,它会在类型转换中给出错误:
private boolean less(Comparable<T> u, Comparable<T> v) {
return u.compareTo(v) < 0;
}
我通过类型转换传递给compareTo的参数来解决问题。但它仍然在给我警告(类型安全:从比较对象T中未经检查)。为什么会如此。难道我做错了什么。实现这一目标的最佳方法是什么。
private boolean less(Comparable<T> u, Comparable<T> v) {
return u.compareTo((T) v) < 0;
}
答案 0 :(得分:1)
初始错误是正确的,并且警告是正确的:你的技巧非常不安全:你不能把v投射到T.
因为你的方法接受两个参数u和v,每个参数都是一个类的实例,它实现了compareTo(T的某个实例)。
确切地说:你可以比较T,v可以比较T。
但是,在内部,你想要比较你和v。绝对没有保证你能做到。
例如,这是正确的:
private static <X> boolean less(Comparable<X> u, X v)
{
return u.compareTo(v) < 0;
}
答案 1 :(得分:1)
由于strnew = strnew + " ";
的类型为u
,Comparable<T>
需要u.compareTo()
。您正在传递T
,v
,这是不兼容的。
您可能会在脑海中假设实现Comparable<T>
的类型与其自身相当。但是在技术层面上没有这样的要求。制作Comparable
类型Foo
对我来说是完全合法的,即它与Comparable<Bar>
进行比较,其中Bar
和Foo
是Bar
完全无关。尝试将Foo
传递到Foo
对象的compareTo
会崩溃。
如果你想制定一个约束条件,即两个参数的类型与自身相同,那么你可以这样做
private <T extends Comparable<? super T>> boolean less(T u, T v) {
return u.compareTo(v) < 0;
}
但是,出于此函数的目的,两个参数属于同一类型的约束在技术上是不必要的(尽管在所有正常用例中都应该如此)。在泛型中,我们总是希望使用可能性最小的限制,就像其他答案所提到的那样,
private <T> boolean less(Comparable<T> u, T v) {
return u.compareTo(v) < 0;
}
在您的评论中,您提到您正在比较Comparable<T>[]
中的元素。这不是一种允许您比较元素的数组。您只知道它是一系列与某个T
相当的元素,但与自身无法比较。更有用的是拥有T[]
,其中T
具有与其自身相当的界限:
class Whatever<T extends Comparable<? super T>> {
//...
T[] yourArray;
}