List apples = new ArrayList(); //1
List fruits = apples; //2
第1行代码显然是对的,但是第2行是否对呢?我们知道Fruit fruit = new Apple(),这样肯定是对的,即苹果肯定是水果,但是第2行在编译的时候会出错。这会让人比较纳闷的是一个苹果是水果,为什么一箱苹果就不是一箱水果了呢?可以这样考虑,我们假定第2行代码没有问题,那么我们可以使用语句fruits.add(new Strawberry())(Strawberry为Fruit的子类)在fruits中加入草莓了,但是这样的话,一个List中装入了各种不同类型的子类水果,这显然是不可以的,因为我们在取出List中的水果对象时,就分不清楚到底该转型为苹果还是草莓了。
public abstract class Shape {
public abstract void draw(Canvas c);
}
public class Circle extends Shape {
private int x,y,radius;
public void draw(Canvas c) { ... }
}
public class Rectangle extends Shape
private int x,y,width,height;
public void draw(Canvasc) { ... }
}
List shapes = new ArrayList();
List super Cicle> cicleSupers = shapes;
cicleSupers.add(new Cicle()); //OK, subclass of Cicle also OK
cicleSupers.add(new Shape()); //ERROR
Object[] oa = new Object[100];
Collectionco = new ArrayList();
fromArrayToCollection(oa, co);// T inferred to be Object
String[] sa = new String[100];
Collectioncs = new ArrayList();
fromArrayToCollection(sa, cs);// T inferred to be String
fromArrayToCollection(sa, co);// T inferred to be Object
Integer[] ia = new Integer[100];
Float[] fa = new Float[100];
Number[] na = new Number[100];
Collectioncn = new ArrayList();
fromArrayToCollection(ia, cn);// T inferred to be Number
fromArrayToCollection(fa, cn);// T inferred to be Number
fromArrayToCollection(na, cn);// T inferred to be Number
fromArrayToCollection(na, co);// T inferred to be Object
fromArrayToCollection(na, cs);// compile-time error
public void go(T t) {
System.out.println("generic function");
}
public void go(String str) {
System.out.println("normal function");
}
public static void main(String[] args) {
FuncGenric fg = new FuncGenric();
fg.go("haha");//打印normal function
fg.go("haha");//打印generic function
fg.go(new Object());//打印generic function
fg.go(new Object());//打印generic function
}
/*代码一:编译时错误*/
public class Erasure{
public void test(int i){
System.out.println("Sting");
}
public int test(int i){
System.out.println("Integer");
}
}
/*代码二:正确 */
public class Erasure{
public void test(List ls){
System.out.println("Sting");
}
public int test(List li){
System.out.println("Integer");
}
}
Listl1 = new ArrayList();
Listl2 = new ArrayList();
System.out.println(l1.getClass() == l2.getClass()); //True
3)instanceof
不能对确切的泛型类型使用instanceOf操作。如下面的操作是非法的,编译时会出错。
Collection cs = new ArrayList();
if (cs instanceof Collection){…}// compile error.如果改成instanceof Collection>则不会出错。
4)泛型数组问题
不能创建一个确切泛型类型的数组。如下面代码会出错。
List[] lsa = new ArrayList[10]; //compile error.
因为如果可以这样,那么考虑如下代码,会导致运行时错误。
List[] lsa = new ArrayList[10]; // 实际上并不允许这样创建数组
Object o = lsa;
Object[] oa = (Object[]) o;
Listli = new ArrayList();
li.add(new Integer(3));
oa[1] = li;// unsound, but passes run time store check
String s = lsa[1].get(0); //run-time error - ClassCastException
ist>[] lsa = new List>[10]; // ok, array of unbounded wildcard type
Object o = lsa;
Object[] oa = (Object[]) o;
Listli = new ArrayList();
li.add(new Integer(3));
oa[1] = li; //correct
String s = (String) lsa[1].get(0);// run time error, but cast is explicit
Integer it = (Integer)lsa[1].get(0); // OK