黑马程序员之反射1

来源:互联网 发布:矩阵数据分析法 编辑:程序博客网 时间:2024/06/05 14:32
 ---------------------- android培训、java培训、期待与您交流! ----------------------

今天学反射,感觉有点难,不好去写,虽然已经复习了好几遍了,加油吧,要学会去挑战!

 

反射的基石:Class,它用来描述类的一类相同的属性,就像信息里面的信息一样,每个类都会有一些共性:我们用类Class表示

得到字节码的三种方法:

类名.class

类的对象.getClass();

Class.forName(“”);加载和查询字符串的所在类

 

八个基本类型加上一个void九个预定意的Class对象

总之:只要是在源程序中出现的类型,都有各自的Class实例对象,如数组int[],void.

数组类型的Class实例对象用Class.isArray()判断是什么类型;

 

理解反射:反射就是把java类中的各种成分映射成相应的java类,把java身上的东西都反射称各种类;

不管是什么方法都可以反射称Method,至于是哪个方法,那么我们就用Method对象来表示

也就是说:一个类中的每个成员都可以用相应的反射API类的一个实例对象来表示,通过调用Class类的方法可以得到这些实例对象,得到实例对象后我们是怎么使用的呢?干什么用呢

我们用构造方法去得到所在的类,修饰符,创建实例对象

反射的应用:

//构造方法的反射的应用:Constructor类:代表某个类中的一个构造方法

得到所有的构造方法:Constructor[]constructors=Class.forName(“”).getConstructors();

得到某一个构造方法:

Constructor constructor=Class.forName(“”).getConstructor();

得到带参数的构造方法:String.class.getConstructora(StringBuffer.class);

用反射的方式实现new String(new StringBuffer(“abc”));

Constructor constructor =String.class.getConstructor(StringBuffer.class);

(String)Construtor.newInstance(new StringBuffer(“abc”));

//这里我们用到了强制装换,在之后的泛型中,我们就不用强制转换了

//调用获得的方法时传递上面想同类型的参数对象

在Class类中也有一个newInstance()也是创建这个类型的对象,其实Class调用的是无参的构造方法,为什么反射比较好用性能:因为每次用到了这个构造方法时,都会缓存起来,下次再用的时候直接就会调用Class的newInstence()方法

//成员变量的反射:.下面我们就对一个类进行反射f

先创建一个对象,通过对象获得类的字节码,然后得到其中的变量字段;

得到字段的字节码:Field fieldY = pt1.getClass().getField(“y”);此时我们得到的是变量y并没有对应到对象身上,然后再取出对象上的变量值:

Field.get(pt1);

再打印出来;

如何获得私有变量的字段:Field fieldX=pt1.getClass.getDeclaredField(“x”);

利用暴力反射去取得值:fieldX.getAccessible(true);

通过改掉别人类里面的字符串中的值来理解成员变量的反射:

我们定义一个独立的方法:private static void changeStringValue(Object obj){

Field[]fields= obj.getClass().getFields();

For(Field field:fields){

If(field.getType()==String.class){

String oldValue=(String)field.get(obj);

String newValue=oldValue.replace(‘b’,’a’);

Field.set(obj,newValue);

}

}

}

同样我们应该覆盖toString()方法

public String toString(){

return str1+”:”+str2+”:”+str3;

}

//成员方法的反射:Method类:

Method methodCharAt=String.class.getMethod(“charAt”,int.class);然后我们用Method对象去调用charAt()如:methodCharAt.imvoke(str1,1);imvoke()是Method方法中的调用方法中的方法;

如果这个方法中第一个参数为null,那么判断这个方法为静态方法;

面向对象很重要,要好好体会;

谁拥有数据,谁就去做这件事的专家;

//对接收数组参数的成员方法的反射:我们这里就反射别人的main()方法

用调用静态方法的方式调用main()方法:类名.main(String[]args);

反过来想一想我们为什么用反射调用呢?

因为我们不知道执行的是哪个类的main()方法

我们只能通过传过来的参数去执行:但我知道类中一定有一个方法

Method mainMethod =Class.forName(startingClassName).getMethod(“main”,String[].class);

mainMethod.imvoke(null,new Object[]{new String[]{}});

注意:jdK1.5为了兼容1.4它对一个数组会打开,因此我们要打两层包:

还有一种解决方法:mainMethod.imvoke(null, (Object)new String[]{“”,””,””}});

今天对反射有种更深的认识了,其实有写东西真的需要时间,虽然,按了好多遍了,但是每一遍都会有不一样的收获

 

 

---------------------- android培训、java培训、期待与您交流! ----------------------详细请查看:http://edu.csdn.net/heima