JAVA的反射机制
定义
-
在JAVA运行时的环境中,对于任意一个类,如何知道这个类的属性和方法?对于任意一个对象,如何调用它的任意一个方法?
-
----答案是Java语言的反射(Reflection)机制
-
----即动态获取类的信息以及动态调用对象的方法的功能。
功能提供
-
- 在运行时构造任意一个类的对象
- 在运行时判断任意一个对象所属的类
- 在运行时判断任意一个类所具有的成员变量和方法
- 在运行时调用任意一个对象的方法
三个动态性质
-
1.运行时生成对象实例
-
2.运行期间掉用方法
-
3.运行时更改属性
运行机制
-
首先我们需要知道java程序是如何被运行的。
-
.java文件---->编译器---->.clss(加载所需的类)---->java虚拟机进行加载---->运行程序
- 此时我们需要注意到的是Java类如果不被Java虚拟机加载,则不能正常运行。而Java的反射机制都是在编译时就已经加载了我们所需要的那个类。
Java Reflection API简介
-
Java反射API用来生成在当前Java虚拟机中的类、接口或者对象的信息。其中Class类是反射的核心类,反射所有的操作都是围绕该类来生成的。通过Class类,我们可以获取类的属性、方法等内容信息。
-
在JDK中,主要由以下类来实现Java反射机制,这些类(除了第一个)都位于java.lang.reflect包中
类 | 功能 |
---|
Class类 | 代表一个类,位于java.lang包下 |
Field类 | 代表类的成员变量(成员变量也称为类的属性) |
Method类 | 代表类的方法 |
Constructor类 | 代表类的构造方法 |
Array类 | 提供了动态创建数组,以及访问数组的元素的静态方法 |
1.使用反射API在运行的时候得到指定类的方法和属性
package cn.happy.reflet.classinfo;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import javax.swing.JOptionPane;
public class ReflectDemo {
public ReflectDemo(){
String classpath=JOptionPane.showInputDialog(null,"");
try {
Class cla=Class.forName(classpath);
Method[] method=cla.getDeclaredMethods();
System.out.println("*************获取方法信息************");
for (Method meth : method) {
System.out.println(meth.toString());
}
System.out.println("*************获取方法信息结束************");
Field[] fileds=cla.getDeclaredFields();
System.out.println("*********获取属性的信息************");
for (Field field : fileds) {
System.out.println(field.toString());
}
System.out.println("*********获取属性的信息************");
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
}
package cn.happy.reflet.classinfo;
public class TestReflect {
public static void main(String[] args) {
ReflectDemo rd=new ReflectDemo();
}
}
2.那么如何获取class对象
-
在主程序中调用
-
每个类被加载后,系统就会为该类生成一个对应的Calss对象,通过该Class对象就可以访问到Java虚拟机中的这个类。
PerSon p=new Person();
Class cla=p.getClass();
Class cla=Person.Class;
Class cla=Class.forName("类的全路径名");
反射用途
-
1、反编译:.class–>.java
-
2、通过反射机制访问java对象的属性,方法,构造方法等
-
3、当我们在使用IDE,比如Ecplise时,当我们输入一个对象或者类,并想调用他的属性和方法是,一按点号,编译器就会自动列出他的属性或者方法,这里就是用到反射。
-
4、反射最重要的用途就是开发各种通用框架。比如很多框架(Spring)都是配置化的(比如通过XML文件配置Bean),为了保证框架的通用性,他们可能需要根据配置文件加载不同的类或者对象,调用不同的方法,这个时候就必须使用到反射了,运行时动态加载需要的加载的对象。
-
5、例如,在使用Strut2框架的开发过程中,我们一般会在struts.xml里去配置Action,比如
<action name="login" class="org.ScZyhSoft.test.action.SimpleLoginAction" method="execute">
<result>/shop/shop-index.jsp</result>
<result name="error">login.jsp</result>
</action>
- 比如我们请求login.action时,那么StrutsPrepareAndExecuteFilter就会去解析struts.xml文件,从action中查找出name为login的Action,并根据class属性创建SimpleLoginAction实例,并用Invoke方法来调用execute方法,这个过程离不开反射。配置文件与Action建立了一种映射关系,当View层发出请求时,请求会被StrutsPrepareAndExecuteFilter拦截,然后StrutsPrepareAndExecuteFilter会去动态地创建Action实例。
- 比如,加载数据库驱动的,用到的也是反射。
Class.forName("com.mysql.jdbc.Driver");