2011-12-20 4 views
2

У меня есть следующий встроенный компаратор.Typechecking и generics в java генерируют предупреждения

private static class SampleSorter implements Comparator<SampleClass>{ 
    public int compare(SampleClass o1, SampleClass o2) { 
     if (o1 instanceof Comparable) { 
      return ((Comparable) o1).compareTo(o2); 
     } else if (o2 instanceof Comparable) { 
      return -((Comparable) o2).compareTo(o1); 
     } 
     return 0; 
    } 
} 

который генерирует следующие предупреждения:

Comparable is a raw type. References to generic type Comparable<T> should be parameterized


И если я вместо параметризации типов, как предложено:

 if (o1 instanceof Comparable) { 
      return ((Comparable<SampleClass>) o1).compareTo(o2); 

Тогда я получаю предупреждение ...

Type safety: Unchecked cast from SampleClass to Comparable<SampleClass>


И если я проверки типов:

if (o1 instanceof Comparable<SampleClass>) { 
     return ((Comparable<SampleClass>)o1).compareTo (o2); 

Я получаю следующее ошибки:

Cannot perform instanceof check against type Comparable<SampleClass> . Use the form Comparable<?> instead since generic type information will be erased at runtime


И опять же, если я следую совету сообщение об ошибке:

if (o1 instanceof Comparable<?>) { 
     return ((Comparable<?>)o1).compareTo (o2); 

Я получаю эту ошибку:

The method compareTo(capture#4-of ?) in the type Comparable<capture#4-of ?> is not applicable for the arguments (SampleClass)


Теперь я не знаю, как procede, я действительно Prefere код, который Предупреждение- и безошибочной. Как создать код без предупреждения с желаемым поведением?

+0

На стороне записки: что произойдет, если o1 сравнима и o2 не? Кажется, что оба не могли сравниться. – oers

ответ

4

У вас есть проблема, так как компилятор не знает, что то, что вы делаете, безопасно. Вместо этого вы должны доверять вы знаете, что вы делаете, и вы можете добавить аннотацию

@SuppressWarnings("unchecked") 

тот он или метод класса и предупреждение исчезнет.

+0

Да, это работает. Но я всегда считал «@ SuppressWarnings» немного уродливым, и это было бы моим последним прибежищем. Возможно, нет лучшего способа, как вы говорите. –

+2

Уродство самонадеянно, потому что вы пытаетесь злоупотреблять языком/libs в любом случае: либо 'SampleClass' должен реализовывать' Comparable', то вам не нужны никакие 'instanceof' и casts. Или вы нарушаете договор «Сопоставимый», а именно, коммутативную и транзитивную части. Чтобы быть чистым, вам нужно будет отступить и подумать об общей картине и не о некоторых пикселях. –

+0

Правда, в моем случае фактический код лежит в огромном унаследованном приложении, что делает общую картину довольно трудно увидеть. –

0

Попробуйте

if (o1 instanceof Comparable<?>) { 
     return ((Comparable<SampleClass>)o1).compareTo (o2); 
+0

Тип безопасности: снят флажок из 'SampleClass' в' Comparable ' –

+0

Использует ли SampleClass Comparable? –

+0

Traxdata: Некоторые подклассы. –