Java反射

1.Java反射

在mybatis中,给了什么类型,mybatis就可以将结果封装映射到给定的类的对象中
<select id="findAdminByld" parameterType="int" resultType="Admin">
<select id="teachers" resultType="com.ffyc.mybatispro.model.Teacher">

框架需要只写一套程序,就可以处理给其的任意类,

框架是如何做到写一套程序,就可以处理任意类了?

以前已知类名的使用方式,可以看做是正向使用类.

框架需要对任意类处理时,只是知道类的名字,通过类的名字动态才去获取类中的信息.

把这种对类的使用方式,称为反向使用.

1.java反射概念及作用

Java反射:是在运行状态中,对于任意一个类,都能够知道这个 类的所有属性和方法;对于任意一个对象,都能够调用它的任意一个 方法和属性;这种动态获取信息以及动态调用对象的方法的功能称为 java语言的反射机制。(在运行状态中在仅知道一个类名时,就可以动态获得类中信息,创建对象,调用对象成员的机制称为java反射机制)

作用: 动态获取类的信息。

2.java反射相关API

2.1.Class类(java.lang.Class)

(1)概念:Class类表示当前正在运行中的类和接口

注意;一旦class文件被加载到内存,就会为其创建一个Class对象。任何类被 使用时都会创建一个Class对象;

Class类是Java反射机制的基础,通过Class类,可以得到一个类的基本 信息。

(2)获得Class类的方法

● Object类中的getClass方法:适用于通过对象获得Class实例的情况

● 类名.class方式:适用于通过类名获得Class实例的情况

● Class类的静态方法 forName(String name)

(3)java创建对象的四种方式

 1.new  +对象名

2.反序列化

3.反射机制  获取到对象的包名和类名

 4.对象克隆

2.2 Constructor类

Constructor是获取对象的构造方法的类

获取Constructor的实例:

1.通过Class实例获得,Class类中定义了如下方法

Constructor<T> getConstructor(Class... parameterTypes)

通过指定参数类型,返回构造方法

(1)getConstructor()  获得指定的公共构造方法

(2).getConstructors();//获得所有公共的构造方法

(3).getDeclaredConstructor();//获得类中任意的构造方法(包含私有)

(4)getDeclaredConstructors();//获得类中所有的构造方法(包含私有)

2.Constructor类可以通过getXXX方法获得构造方法的基本信息.

● getName:返回构造方法的名字

除了获得构造方法的基本信息,还可以创建实例

● newInstance(Object... initargs) :创建实例

2.3 Field类

Field类作用是获取到对象的成员变量

1.获得Field类实例:

 public Field getField(String name)通过指定Field名字,返回 Field实例.   注意Field的访问权限

(1)getField("成员变量");//获得指定名称的公共的成员变量

(2)getFields() 获得所有的公共成员变量

(3)getDeclaredField( "成员变量t");//获得指定名称的成员变量,包含私有的

(4)getDeclaredFields( );//获得所有的成员变量,包含私有的

2.Field类的作用

 Field类将类的属性进行封装,可以获得属性的基本信息、属性的值,也

可以对属性进行赋值.

 getName:返回属性的名字

 set:设置属性值

2.4  Method类

1.获取Method类的实例:

Method getMethod(String name, Class... parameterTypes) : 通过指定方法名,参数类型,返回一个Method实例

2.Method类作用

1. Method类将类中的方法进行封装,可以动态获得方法的信息,例如

● getName:获得方法名字

● getParameterTypes:获得方法参数类型

2.除了动态获得方法信息外,Method还能动态调用某一个对象的具体方法

● invoke(Object obj, Object... args) :使用obj调用该方法,参数为args

2.反射案例

1.演示通过属性的get和set方法,对类中的私有属性进行取值,操作。

User类:

public class Test3 {
    public static void main(String[] args) throws ClassNotFoundException, IllegalAccessException, InstantiationException, NoSuchMethodException, InvocationTargetException, NoSuchFieldException {

        //使用反射机制时,只知道类的名称(包名+类名)
        String classname="com.ffyc.javaReflect.User";
        /* String classname="com.ffyc.javaReflect.Car";*/

//        1.通过类名获得到类的Class对象
       Class clazz= Class.forName(classname);

//        2.通过类的Class对象,创建对象
         Object object=clazz.newInstance()
       
        /*模拟从数据库拿到的数据*/
        HashMap<String,String> map=new HashMap<>();
        map.put("account", "admin");
        map.put("password", "111");
           Field[] fields=clazz.getDeclaredFields();//获得类中所有成员变量
        for(Field field:fields){
            field.setAccessible(true);//允许访问操作私有的属性
         field.set(object,map.get(field.getName()) );

        }
        System.out.println(object);
    }
}

2.自定义java对象转json工具类

类同上

public class JsonUtil {
    public  static String objectToJson(Object object) throws ClassNotFoundException, IllegalAccessException, InstantiationException, NoSuchMethodException, InvocationTargetException {
     // 获取到类的Class对象
        Class clazz=object.getClass();
String json="{";
//获取类中所有属性
        Field[] declaredFields =clazz.getDeclaredFields();
        for(Field field:declaredFields){
//生成属性get方法名字
            String getmethod = "get" + field.getName().substring(0, 1).toUpperCase() + field.getName().substring(1);
          //获得方法对象
            Method method=clazz.getMethod(getmethod);
//            调用方法
      String value=(String)method.invoke(object);
//      把属性名称和和值拼接成键值
            json+=field.getName()+":"+value+",";
        }
        json=json.substring(0,json.length()-1);
json+="}";

return json;
    }

    public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, InvocationTargetException {
        User user=new User();
        user.setAccount("admin");
        user.setPassword("111");

        Car car=new Car();
        car.setName("bbb");
        car.setColor("red");

        System.out.println(JsonUtil.objectToJson(user));
        System.out.println(JsonUtil.objectToJson(car));
    }
}

3.反射机制的优缺点

优点:

 1.增加程序的灵活性,可以在运行的过程中动态对类进行修改和操作

 2.提高代码的复用率,比如动态代理

 3.可以在运行时轻松获取任意一个类的方法、属性,并且还能通过反射进行动态调用

缺点:

 1.反射会涉及到动态类型的解析,导致性能要比非反射调用更低

 2.使用反射技术通常要在一个没有安全限制的程序运行.

 3.反射可以绕过一些限制访问的属性或者方法,可能会导致破坏代码本身的抽象 性

  • 23
    点赞
  • 16
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值