java泛型检查只在编译期有效,而反射是在运行期的调用机制。
比如下面这个例子:
Java代码 Map map = new HashMap();
String key = "key";
Integer val = new Integer(1);
Method m = HashMap.class.getDeclaredMethod("put", new Class[] { Object.class, Object.class });
m.invoke(map, key, val);
System.out.println(map); //{key=1}
System.out.println(map.get(key)); // java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.String
}
用反射进行put,绕过了泛型检查;get时泛型会自动进行类型转换,从而导致了ClassCastException
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.ArrayList;
public class Reflect {
@SuppressWarnings("unchecked")
public static void main(String[] args) {
ArrayList list = new ArrayList(10);
list.add(1);
list.add(3);
list.add(4);
//由于泛型检查类型无法add处Integer之外的其他类型
//list.add("hello");
//使用反射机制绕过泛型检查
Class c = list.getClass();
Method method = null;
try {
method = c.getDeclaredMethod("add", Object.class);//取得add方法
method.invoke(list, "hello");
} catch (SecurityException e) {
e.printStackTrace();
} catch (NoSuchMethodException e) {
e.printStackTrace();
} catch (IllegalArgumentException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
System.out.println(list.toString());
}
}1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
输出结果:
[1, 3, 4, hello]