I am writing a generic collection based on a binary tree model.
class MyTree <T extends Comparable<T>> extends AbstractCollection<T>{...}
The underlying Node<T>
class (among others) contains the following methods:
public Node<T> getLeft() // left Node
public Node<T> getRight() // right Node
public T getValue() // value stored in the Node
I want to override the method boolean contains(Object o)
of the interface AbstractCollection<T>
to have the possibility to check for Object
's of a type other than T
.
For the tree traversal in O(log n) the generic type T
must implement Comparable<T>
, so it has the method compareTo(T t)
.
My code:
@Override
public boolean contains(Object o){
T t = (T) o; // produces warning (see below)
BSNode<T> currentNode = this.root;
while(currentNode != null){
if(currentNode.getValue().equals(o)) {return true;}
if(currentNode.getValue().compareTo(t) < 0) {currentNode = currentNode.getRight();}
if(currentNode.getValue().compareTo(t) > 0) {currentNode = currentNode.getLeft();}
}
return false;
}
The problem is that I can not just cast Object o
to T t
for using compareTo(T t)
. Technically the Object
's are castable to T
, but as T
is a generic type, I get this warning:
warning: [unchecked] unchecked cast
T t = (T) o;
^
required: T
found: Object
where T is a type-variable:
T extends Comparable<T> declared in class MyTree
Can someone either
@SuppressWarnings("unchecked")
,Object
to T
,Thanks a lot!
If you would like to have unrestricted searches, you need to do a cast. You can add instanceof
to guard the cast from exceptions, but that is not ideal either.
Consider changing the bounds of T
as follows:
class MyTree <T extends Comparable<? super T>> extends AbstractCollection<T>{...}
Since you do an override, suppressing the warning is pretty much required. The cast should look as follows:
@SuppressWarnings("unchecked")
Comparable<? super T> t = (Comparable<? super T>) o;
See the source of getEntry
method of java.util.TreeMap
for an example of how it is done in Java source (they do it for the same reason - the need to override a method with a signature taking Object
).