Ksh*_*rma 13 java generics java-8
我有以下代码:
public static void main(String[] args) {
List<String> s = new ArrayList<String>();
s.add("kshitiz");
//This is not typesafe. It should blow up at runtime
List<Integer> i = new ArrayList(s);
System.out.println(i.get(0));
}
Run Code Online (Sandbox Code Playgroud)
这个程序运行正常,并打印kshitiz.如果我用以下内容替换最后一行,它只会失败:
System.out.println(i.get(0).getClass());
Run Code Online (Sandbox Code Playgroud)
例外:
Exception in thread "main" java.lang.ClassCastException: java.lang.String cannot be cast to java.lang.Integer
Run Code Online (Sandbox Code Playgroud)
这里发生了什么?
muu*_*ued 13
我想你知道,泛型类型在运行时已经消失了.现在,看看幕后发生了什么,让我们来看看这段代码
public static Class<?> getClass(final Object object) {
return object.getClass();
}
public static void main(final String[] args) {
final List<String> s = new ArrayList<String>();
s.add("kshitiz");
// This is not typesafe. It should blow up at runtime
final List<Integer> i = new ArrayList(s);
System.out.println(getClass(i.get(0)));
System.out.println(i.get(0).getClass());
}
Run Code Online (Sandbox Code Playgroud)
和javap -c的输出
[...]
26: getstatic #8 // Field java/lang/System.out:Ljava/io/PrintStream;
29: aload_2
30: iconst_0
31: invokeinterface #9, 2 // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
36: invokestatic #10 // Method getClass:(Ljava/lang/Object;)Ljava/lang/Class;
39: invokevirtual #11 // Method java/io/PrintStream.println:(Ljava/lang/Object;)V
42: getstatic #8 // Field java/lang/System.out:Ljava/io/PrintStream;
45: aload_2
46: iconst_0
47: invokeinterface #9, 2 // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
52: checkcast #12 // class java/lang/Integer
55: invokevirtual #2 // Method java/lang/Object.getClass:()Ljava/lang/Class;
58: invokevirtual #11 // Method java/io/PrintStream.println:(Ljava/lang/Object;)V
61: return
Run Code Online (Sandbox Code Playgroud)
所以你看到在第二次调用中,String被强制转换为Integer,而在第一种情况下,它被视为一个对象.因此,只要像任何其他对象一样处理String,一切都很好,但只要调用列表的元素类型的方法,对象就会转换为该类型.
| 归档时间: |
|
| 查看次数: |
153 次 |
| 最近记录: |