概述
JAVA反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法;对于任意一个对象,都能够调用它的任意一个方法和属性;这种动态获取的信息以及动态调用对象的方法的功能称为java语言的反射机制。要想解剖一个类,必须先要获取到该类的字节码文件对象。而解剖使用的就是Class类中的方法.所以先要获到每一个字节码文件对应的Class类型的对象.
- 我们可以通过一个类获取这个类中的方法,变量,构造方法等属性,并将这些属性映射成一个个对象来使用。
反射的使用
1.获取Class对象的三种方式:
- 通过对象的getClass方法获取(先得拥有这个对象,既然有对象那么再去用反射意义不大)
Apple apple=new Apple();Class<? extends Apple> aClass1 = apple.getClass();
- 通过使用Class类的forName通过类名获取
name="org.example.day19.Test.reflection.Orange";Orange orange = (Orange) createObjectForName(name);
- 直接通过类名点class方法获取(需要先进行导包)
Class<Apple> appleClass = Apple.class;
注意:在运行期间,一个类,只有一个Class对象产生。
2.通过反射获取构造方法并使用:
- public Constructor[] getConstructors():*获取所有公有构造方法*
Class<Apple> appleClass = Apple.class;
Constructor<?>[] constructors = appleClass.getConstructors();
for (Constructor<?> constructor : constructors) {System.out.println(constructor);
}
/*public org.example.day19.Test.reflection.Apple(java.lang.String,int)
public org.example.day19.Test.reflection.Apple()*/
- *public Constructor[] getDeclaredConstructors():*获取所有的构造方法(包括私有的,默认的,公有的,受保护的)
Class<Apple> appleClass = Apple.class;
Constructor<?>[] constructors = appleClass.getDeclaredConstructors();
for (Constructor<?> constructor : constructors) {System.out.println(constructor);
}
/*public org.example.day19.Test.reflection.Apple(java.lang.String,int)
public org.example.day19.Test.reflection.Apple()*/
- *public Constructor getConstructor(Class… parameterTypes):*获取所有的公有无参构造方法
Class<Apple> appleClass = Apple.class;
Constructor<Apple> constructor = appleClass.getConstructor(null);
System.out.println(constructor);
- *public Constructor getDeclaredConstructor(Class… parameterTypes):*获取所有的无参构造方法(包括私有的,默认的,公有的,受保护的)
Class<Apple> appleClass = Apple.class;
Constructor<Apple> constructor=appleClass.getDeclaredConstructor(String.class,Integer.class);
System.out.println(constructor);
**调用构造方法:**Constructor–>newInstance(Object… initargs)
- **newInstance是 Constructor类的方法(管理构造函数的类)
**
api的解释为:
newInstance(Object… initargs)使用此 Constructor 对象表示的构造方法来创建该构造方法的声明类的新实例,并用指定的初始化参数初始化该实例。它的返回值是T类型,所以newInstance是创建了一个构造方法的声明类的新实例对象并为之调用。
3.获取成员变量并调用:
- Field[] getFields():获取所有的"公有字段"
Class<Apple> appleClass = Apple.class;
Field[] fields = appleClass.getFields();
for (Field field : fields) {System.out.println(field.getName());
}
- Field[] getDeclaredFields():获取所有字段,包括:私有、受保护、默认、公有
Class<Apple> appleClass = Apple.class;Field[] fields = appleClass.getDeclaredFields();for (Field field : fields) {System.out.println(field.getName());}
- public Field getField(String fieldName):获取某个"公有的"字段;
Field f = Apple.class.getField("price");System.out.println(f);//获取一个对象Object obj = Apple.class.getConstructor().newInstance();//产生Student对象--》Student stu = new Student();//为字段设置值f.set(obj, "price");//为Student对象中的name属性赋值--》stu.name = "刘德华"//验证Apple stu = (Apple) obj;System.out.println("验证价格:" + stu.getPrice());
- public Field getDeclaredField(String fieldName):获取某个字段(可以是私有的)
Class<Student> studentClass = Student.class;Student student=new Student();Field[] fields = studentClass.getDeclaredFields();for (Field field : fields) {field.setAccessible(true);resultSet.getObject(field.getName());field.set(student,resultSet.getObject(field!=null?field.getName():null));}
4.获取成员方法并调用:
- public Method[] getMethods():获取所有"公有方法";(包含了父类的方法也包含Object类)
Method[] methods = Apple.class.getMethods();
for (Method method : methods) {System.out.println(method.getName());
}
- public Method[] getDeclaredMethods():获取所有的成员方法,包括私有的(不包括继承的)
Method[] methods = Apple.class.getDeclaredMethods();
for (Method method : methods) {System.out.println(method.getName());
}
- *public Method getMethod(String name,Class<?>… parameterTypes):*通过方法名和参数列表获取当个方法
Method methods = Apple.class.getMethod("appM");
System.out.println(methods);
- public Method getDeclaredMethod(String name,Class<?>… parameterTypes):获取私有方法、
Method methods = Apple.class.getDeclaredMethod("appM",Integer.class);
System.out.println(methods);