明明我自己能直接new一个对象,为什么它要绕一个圈子,先拿到Class对象,再调用Class对象的方法来创建对象呢,这不是多余吗?
为什么需要反射:
我现在认为用反射主要有两个原因:
提高程序的灵活性
屏蔽掉实现的细节,让使用者更加方便好用
列举两个例子:
1.连接数据库时,加载数据库相关配置是,配置都是在配置文件中配置的,程序其实是通过反射获取的,代码中不想写死:
例如:
//获取配置文件的信息
driver = properties.getProperty("driver");
url = properties.getProperty("url");
username = properties.getProperty("username");
password = properties.getProperty("password");
2.spring接收请求时,前台的入参接收时,咱们用对象来接收,其实也是反射‘
额外了解:
一个对象的加载过程,
1.一个.java的文件经过javac命令编译成功后,得到一个.class的文件
2.当我们执行了初始化操作(有可能是new、有可能是子类初始化 父类也一同被初始化、也有可能是反射...等),会将.class文件通过类加载器装载到jvm中
3.将.class文件加载器加载到jvm中,又分了好几个步骤,其中包括 加载、连接和初始化
4.其中在加载的时候,会在Java堆中创建一个java.lang.Class类的对象,这个Class对象代表着类相关的信息。
反射就是围绕着Class对象和java.lang.reflect类库来学习,就是各种的AP
知道获取Class对象的几种途径
通过Class对象创建出对象,获取出构造器,成员变量,方法
通过反射的API修改成员变量的值,调用方法
想要使用反射,我先要得到class文件对象,其实也就是得到Class类的对象
Class类主要API:
成员变量 - Field
成员方法 - Constructor
构造方法 - Method
获取class文件对象的方式:
1:Object类的getClass()方法
2:数据类型的静态属性class
3:Class类中的静态方法:public static Class ForName(String className)
--------------------------------
获取成员变量并使用
1: 获取Class对象
2:通过Class对象获取Constructor对象
3:Object obj = Constructor.newInstance()创建对象
4:Field field = Class.getField("指定变量名")获取单个成员变量对象
5:field.set(obj,"") 为obj对象的field字段赋值
如果需要访问私有或者默认修饰的成员变量
1:Class.getDeclaredField()获取该成员变量对象
2:setAccessible() 暴力访问
---------------------------------
通过反射调用成员方法
1:获取Class对象
2:通过Class对象获取Constructor对象
3:Constructor.newInstance()创建对象
4:通过Class对象获取Method对象 ------getMethod("方法名");
5: Method对象调用invoke方法实现功能
如果调用的是私有方法那么需要暴力访问
1: getDeclaredMethod()
2: setAccessiable();