1.反射是Java提供的一种运行机制,代码运行时动态的获取一个类型的各种信息,以及相关的一系列操作
Java中每一种类型,都有且仅有一个Class对象与之对应,每种类型在进行类加载之后,JVM会在内存中自动生成一个Class类型对象
Student.java---->Student.class--->类加载--->成功----->内存中产生Class类型对象
2.反射中重要的类和包:反射机制中的常见类的含义
java.lang包下:
Class 类 对java中所有类型抽象而得来的
package类 对java中所有包抽象而得来的
java.lang.reflect包下:
Modifier 类 对java中所有修饰符抽象而得来的
Field 类 对java中所有属性抽象而得来的
Method 类 对java中所有方法抽象而得来的
Constructor 类 对java中所有构造器抽象而得来的
Array 类 提供了对数组对象的动态访问
ParameterizedType 接口 在反射中表示参数化类型
例如:List<String> Point<Long,Long>等这种带泛型的类型
3.获得一个类类型的Class对象的三种方式
以上几种情况中,所以最多的还是类类型的Class对象
1.使用对象调用getClass方法获得
getClass是Object中的final修饰的方法,每个对象都可以调用而且不能重写
Student s = new Student();
Class c = s.getClass();
2.使用类名获得
Class c = Student.class;
3.使用Class类中的forName方法获得
//这种方法很灵活,只需一个String类型参数即可
//而String类型的数据改变起来很容易
//注意该方法是会抛出异常的
Class c = Class.forName("com.briup.test.Student");
注:以上三种方法获得的同一个对象(==比较),因为每个类型内存都有且只有一个Class类型对象
4.创建任意类的对象
public Object test(String className){
Class<?> c=Class.forName(className);
Object obj = c.newInstance();
return obj;
}
注:在开发中要保证无参构造器的存在,否则在反射的时候会很麻烦。
5.使用Class类型对象获得类中的信息
1.获得该类所处的包的信息
Student s = new Student();
Class c = s.getClass();
System.out.println(c.getPackage().getName());
2.获得该类的修饰符信息
//每个修饰符对应一个int值
//如果有多个修饰符则int值相加
Student s = new Student();
Class c = s.getClass();
System.out.println(c.getModifiers());
这里涉及到Modifier这个类,这个类中定义了一系列的修饰符所对应的值
3.获得该类的全限定类名
Student s = new Student();
Class c = s.getClass();
System.out.println(c.getName());
4.获得该类的父类的Class对象
Student s = new Student();
Class c = s.getClass();
//superclass表示其父类型的Class对象
Class superclass = c.getSuperclass();
System.out.println(superclass.getName());
例如:
Class c = Object.class;
Class superclass = c.getSuperclass();
System.out.println(superclass.getName());
//运行报错,因为Object没有父类
例如:
//判断c1是不是c2的子类型
//判断c3是不是c2的子类型
Class c1 = Student.class;
Class c2 = Person.class;
Class c3 = String.class
System.out.println(c2.isAssignableFrom(c1));//true
System.out.println(c2.isAssignableFrom(c3));//false
5.获得该类所实现的接口类型的Class对象
Student s = new Student();
Class c = s.getClass();
Class[] interfaces = c.getInterfaces();
for(Class clazz:interfaces){
System.out.println(clazz.getName());
}
例如:
//判断c1是不是c2的实现类
//判断c3是不是c2的实现类
Class c1 = Student.class;
Class c2 = Action.class;
Class c3 = String.class
System.out.println(c2.isAssignableFrom(c1));//true
System.out.println(c2.isAssignableFrom(c3));//false
6.获得该类中所有的属性
Student s = new Student();
Class c = s.getClass();
Field[] declaredFields = c.getDeclaredFields();
for(Field f:declaredFields){
System.out.println(f.getModifiers());
System.out.println(f.getType().getName());
System.out.println(f.getName());
}
注:
getDeclaredFields()方法返回类中声明的属性,包括私有的
getFields()方法只返回类中public修饰的属性,包括继承的
例如:
//获得某个指定的属性(也包括私有属性)
Student s = new Student();
Class c = s.getClass();
Field f = c.getDeclaredField("score");
System.out.println(f.getModifiers());
System.out.println(f.getType().getName());
System.out.println(f.getName());
7.获得该类中所有的方法
Student s = new Student();
Class c = s.getClass();
Method[] declaredMethods = c.getDeclaredMethods();
for(Method m:declaredMethods){
System.out.println(m.getModifiers());
System.out.println(m.getReturnType().getName());
System.out.println(m.getName());
System.out.println(Arrays.toString(m.getParameterTypes()));
System.out.println(Arrays.toString(m.getExceptionTypes()));
}
注:
getDeclaredMethods()方法返回类中声明的方法,包括私有的
getMethods()方法只返回类中public修饰的方法,包括继承的
例如:
//获得某个指定的方法(也包括私有方法)
Student s = new Student();
Class c = s.getClass();
Method m = c.getDeclaredMethod("print");
System.out.println(m.getModifiers());
System.out.println(m.getReturnType().getName());
System.out.println(m.getName());
System.out.println(Arrays.toString(m.getParameterTypes()));
System.out.println(Arrays.toString(m.getExceptionTypes()));
注:反射重载方法会报出:java.lang.NoSuchMethodException: java.lang.String.valueOf()
8.获得该类中所有的构造器
Student s = new Student();
Class c = s.getClass();
Constructor[] declaredConstructors = c.getDeclaredConstructors();
for(Constructor con:declaredConstructors){
System.out.println(con.getModifiers());
System.out.println(con.getName());
System.out.println(Arrays.toString(con.getParameterTypes()));
System.out.println(Arrays.toString(con.getExceptionTypes()));
}
注:
getDeclaredConstructors()方法返回类中所有构造器
getConstructors()方法只返回类中public修饰的构造器
例如:
//获得某个指定的构造器(也包括私有构造器)
Student s = new Student();
Class c = s.getClass();
Constructor con = c.getDeclaredConstructor(double.class);
System.out.println(con.getModifiers());
System.out.println(con.getName());
System.out.println(Arrays.toString(con.getParameterTypes()));
System.out.println(Arrays.toString(con.getExceptionTypes()));
9.获得父类型中的泛型的真实类型:麻烦 略……
10.获得类中的注解:使用反射也可以获得类中的注解,我在开发时没用过,略……
原文:https://www.cnblogs.com/Magic-Li/p/12813537.html