Java反射机制

来源:互联网 发布:知乎 手工皮具 编辑:程序博客网 时间:2024/06/05 11:07

Java反射机制:
思想:将一个类的各个组件映射成对应的对象,从而可以从对整体的操作转移到对部分组件的操作.

属性:Field
方法:Method
包:Package
构造方法:Constructor

核心类Class:

Java程序在运行时,Java运行时系统一直对所有的对象进行所谓的运行时类型标识,这项信息纪录了每个对象所属的类。虚拟机通过使用运行时类型信息选择正确方法去执行,用来保存这些类型信息的类是Class类。

Class类封装一个对象和接口运行时的状态,当装载类时,Class类型的对象自动创建。 每个对象都是相应的一个Class的实例,一组对象的所有成员变量具有相同的属性和方法,那么每个组员元素在jvm运行时已相同的Class对象出现.每个组对象的基类为Class,Class对象记录相应的对象的所有基本信息,以字节码的形式存储在内存静态区域

通俗来讲:Class类比一个模具(类),模具定义了一个产品的规格,例如材料、尺寸、加工工艺,按照模具的使用要求就可以实现产品(对象实例)的批量生产

测试类:

package com.zhiwei.reflection;class Person{    private String name;    private int age;    private String dept="Science";    public Person(String name, int age) {        super();        this.name = name;        this.age = age;    }    public void show(){        System.out.println(name+"--"+age+"--"+dept);    }}

Class获取的三种方式:

Person person = new Person("squirrel", 10);        Class clazz01 = Person.class;        Class clazz02 = Class.forName("com.zhiwei.reflection.Person");        Class clazz03 = person.getClass();        System.out.println(clazz01 == clazz02);        System.out.println(clazz01 == clazz03);

结果:true true
结论:三种方式获取的得到的对象是一样的

①:对类的属性操作

   //获取定义的属性,如果使用getFields()方法,private类型的属性不会显示    Field[] fields = clazz01.getDeclaredFields();          for(Field field:fields){            System.out.println("属性名:"+field.getName()+",属性类型:"+field.getType());        }

结果:
这里写图片描述

②:对类的普通方法操作:

Method[] methods = clazz01.getMethods();  //获取所有方法        for(Method method:methods){            System.out.println("方法名:"+method.getName()+",参数:"+method.getParameterCount()+",参数类型:"+method.getParameterTypes());        }

结果:
这里写图片描述

③:对类的构造函数的操作

Constructor[] constructors = clazz01.getConstructors();        for(Constructor constructor:constructors){            Parameter[] parameters = constructor.getParameters();            StringBuffer sb = new StringBuffer("构造函数参数类型:");            for(Parameter parameter:parameters){                sb.append(parameter.getParameterizedType()+",");            }            System.out.println(sb.deleteCharAt(sb.length()-1));        }

结果:
这里写图片描述

④:构造函数的应用

Constructor constructor = constructors[0];        Person ps = (Person) constructor.newInstance("zhangsan",14); //对象实例化        ps.show();

结果:
这里写图片描述

Java反射机制的一个小案例01:修改对象实例的属性值

        person.show();        Field field = clazz01.getDeclaredField("dept");        field.setAccessible(true);        System.out.println("原属性值:"+(String)field.get(person));        field.set(person, "music");        person.show();

结果:
这里写图片描述
分析:从person的show()方法打印的信息看出,person实例的属性信息确实被修改。

 Field field = clazz01.getDeclaredField("dept");

相当于获取一个产品的设计参数

field.set(person, "music");

person这个产品的设计参数dept需要个性化定制,改为“music”,set就是将设计参数和产品进行关联,表面只改person的dept属性值

补充:

 field.setAccessible(true);

这个用于设置对象的private修饰的属性访问特定,否则private修饰的属性无法直接访问

Java反射机制的一个小案例02:通过反射机制调用目标方法(回调机制在框架中经常使用)

 Method method = clazz01.getMethod("show");        method.invoke(person);

invoke方法第一个参数为目标对象,第二个参数开始都是方法的参数,这里利用JDK的可变参数的特性

1 0