This question is about the relation of an interface to the class which implements the interface. I can not see how this or this answers the question.
I created an interface Boxed
and an abstract generic class Box
, which implements the interface. Then I create two concrete classes IntegerBox
and StringBox
. Then I created a list of elements, which extend Box
with an IntegerBox
value and a StringBox
value. So far so good.
Now I want to assign List<? extends Box>
to List<Boxed>
. My expectation is, that this should be valid, because whatever extends Box
implements also Boxed
. But the compiler does not allow me. This is the error:
main.java:29: error: incompatible types: List<CAP#1> cannot be converted to List<Boxed>
List<Boxed> lb2 = laeb; // does not compile, although every value which extends Box implements Boxed
^
where CAP#1 is a fresh type-variable:
CAP#1 extends Box from capture of ? extends Box
1 error
I can copy the list:
List<? extends Box> laeb = List.of (new IntegerBox(42), new StringBox("answer"));
List<Boxed> lb1 = new ArrayList<> (laeb);
Every element of the type ? extends Box
is used to create a value if the type Boxed
. But the assignment reports an incompatible type. Why?
import java.util.List;
import java.util.ArrayList;
public class main
{
static interface Boxed { }
static abstract class Box<T> implements Boxed
{
T content;
Box (T content) { this.content = content; }
}
static class IntegerBox extends Box<Integer> { IntegerBox (Integer content) { super (content); } }
static class StringBox extends Box<String> { StringBox (String content) { super (content); } }
public static void main (String ...arguments) throws Exception
{
IntegerBox i = new IntegerBox(42);
StringBox s = new StringBox("answer");
List<? extends Box> laeb = List.of (i, s);
Boxed b0 = i; // => IntegerBox is compatible with Boxed
Boxed b1 = s; // => StringBox is compatible with Boxed
List<Boxed> lb1 = new ArrayList<> (laeb); // List<Boxed> can be created by values of "? extends Box"
List<Boxed> lb2 = laeb; // does not compile, although every value which extends Box implements Boxed
}
}