黑马程序员技术交流社区

标题: 有没有大神可以详细的讲解一下“反射”? [打印本页]

作者: 曹操001    时间: 2015-7-13 00:49
标题: 有没有大神可以详细的讲解一下“反射”?
看了好几遍视频了,感觉还是不懂.,所以拜求各位大神!
作者: Overheat    时间: 2015-7-13 00:49
其实就是动态加载一个指定的类,并获取该类中的所有的内容。而且将字节
码文件封装成对象,并将字节码文件中的内容都封装成对象,这样便于操作这些成员。
简单说:反射技术可以对一个类进行解剖。 反射的好处:大大的增强了程序的扩展性。
反射的好处,把代码动态化,提高了代码的灵活度减少了代码量!(假如将一个对象转化为另一个对象,或者从数据库导出对象。用反射就无需更改原有java逻辑代码。易维护)
反射的缺点,代码灵活度增大了,自然会带来效率的问题,因此,大量使用反射会带来效率低的问题!
反射不可随便用,整个系统中的反射用的过多,对系统性能有影响
反射的应用:用于实现一些框架的原理,或在java类中解析xml或properties里面的配置文件内容,得到一个字符串,然后用反射,根据这个字符串获得某个类的实例,这样就可以动态的配置一些信息,使日后维护起来比较方便
 反射的基本步骤: 
1、获得Class对象,就是获取到指定的名称的字节码文件对象。
2、实例化对象,获得类的属性、方法或构造函数。
3、访问属性、调用方法、调用构造函数创建对象。
 获取这个Class对象,有三种方式: 
1:通过每个对象都具备的方法getClass来获取。弊端:必须要创建该类对象,才可以调用getClass方法。 
2:通过对象的class属性获得。每一个数据类型(基本数据类型和引用数据类型)都有一个静态的属性Method。弊端:必须要先明确该类。 
 前两种方式不利于程序的扩展,因为都需要在程序使用具体的类来完成。 
3:使用的Class类中的方法,静态的forName方法。 
 指定什么类名,就获取什么类字节码文件对象,这种方式的扩展性最强,只要将类名的字符串传入即可。
作者: mortonwyj    时间: 2015-7-24 12:26
反射:
java反射机制的定义:对于任意一个类(class文件),都能知道这个类的所有属性和方法;对于任意一个对象,都能调用它的任意一个方法和属性;这种动态获取的信息以及动态调用对象方法的功能被称为java语言的反射

动态获取类中信息,就是java反射(可以理解为对类的解剖)

想要对一个类文件进行解剖,只要获取到该类的字节码文件对象即可

(P.S.所谓的框架就是对外提供一些接口,对功能进行扩展,由实现类按照这个接口标准去实现。而框架内部内部要操作这些实现类的对象,只需读取配置文件即可,利用反射技术创建这个实现类的对象并且调用相应的方法完成一些操作)

Class类就是字节码文件类,要解剖类,只需得到class类的对象即可


获取Class类对象(字节码文件对象)有3中方式:
1.Object类中的getClass()方法
Person p = new Person();
Class clazz = p.getClass();
2.类的静态属性.class
Class clazz = Person.class;
3.Class类的forName(String name)方法
String className = "cn.itcast.bean.Person";
Class clazz = Class.forName(className);


获取Class中的构造方法:
1.调用空参构造函数来获取对象
Object obj = clazz.newInstance();
2.调用有参数的构造函数来获取对象
Constructor constructor = clazz.getConstructor(int.class, String.class);
Object obj = constructor.newInstance(22,"小明");

对比一下:都是newInstance()方法得到对象,但是一个是直接的,一个是间接的(constructor)



获取Class中的字段:

Field field = clazz.getField("age");---getField()只能获取所有可访问的公关字段,private获取不到
Field field = clazz.getDeclaredField("age");---可以访问私有字段
field.aetAccessible(true);---对私有字段的访问取消权限检查,暴力访问
field.set(obj , 21);


获取Class中的方法:
Method[] methods = clazz.getMethods();---获取的都是公有方法
methods = clazz.getDeclaredMethods();---获取所有的方法(包括石油)
Method method = clazz.getMethod("show",null);---获取某个空参函数
Method method = clazz.getMethod(







欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2