Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

upcast from List<subclass> to List<superclass> via List<?>

I have a class A and a class B extends A

In another class C I have a field

private List<B> listB;

Now, for some unusual reason, I have to implement this method in C

public List<A> getList();

I tried to do so by forcing an upcast of listB field to List<A> via a List<?> cast:

public List<A> getList(){
    return (List<A>)(List<?>)listB;
}

Clients should do

List<A> list = getList();
for(A a:list){
    //do something with a
}

I did some test and it seems work correctly, but honestly I am not sure of the all possible implications.

Is this solution correct? And Is it the best solution?

Thanks for your answers.

like image 660
Max S Avatar asked Jul 07 '10 13:07

Max S


People also ask

How do you cast a List of Supertypes to a List of subtypes?

Try the following: List<TestA> result = new List<TestA>(); List<TestB> data = new List<TestB>(); result.

Can subclass be cast to superclass?

Casting from a subclass to a superclass is called upcasting. Upcasting is closely related to inheritance — another core concept in Java. It's common to use reference variables to refer to a more specific type. And every time we do this, implicit upcasting takes place.

How do you cast a superclass to a subclass in Java?

You can try to convert the super class variable to the sub class type by simply using the cast operator. But, first of all you need to create the super class reference using the sub class object and then, convert this (super) reference type to sub class type using the cast operator.


1 Answers

No, this isn't generally type-safe. The client shouldn't be able to do

List<A> list = getList();

because otherwise they could write

list.add(new C()); // Where C extends A

Then the original code which knows about the list as a List<B> will have problems when it tries to use it, assuming that every element is compatible with B.

You could either wrap the original list to make it read-only, effectively - or make getList return a List<? extends A>, which means that clients won't be able to add items to it anyway.

If the list implementation you're using is unmodifiable, then it won't actually cause problems - but I'd still personally avoid it where possible.

like image 139
Jon Skeet Avatar answered Sep 28 '22 08:09

Jon Skeet