Насколько я понимаю, универсальные типы являются инвариантами, поэтому, если у нас есть B
в качестве подтипа A
, то List<B>
имеет никакого отношения к List<A>
. Таким образом, приведение не будет работать для List<A>
и List<B>
.
Из Effective Java Third Edition у нас есть следующий фрагмент кода:
// Generic singleton factory pattern
private static UnaryOperator<Object> IDENTIFY_FN = (t) -> t;
@SuppressWarnings("unchecked")
public static <T> UnaryOperator<T> identifyFunction() {
return (UnaryOperator<T>) IDENTIFY_FN; //OK But how, why?
}
public static void main(String[] args) {
String[] strings = {"a", "b", "c"};
UnaryOperator<String> sameString = identifyFunction();
for (String s : strings) {
System.out.println(sameString.apply(s));
}
}
Здесь я в замешательстве. Мы привели IDENTIFY_FN
, тип которого UnaryOperator<Object>
, к UnaryOperator<T>
, который имеет другой параметр типа.
Когда происходит стирание типа, String является подтипом Object, но, насколько я знаю, UnaryOperator<String>
не является подтипом UnaryOperator<Object>
.
Объект и T как-то связаны? И как происходит литье в этом случае?