Crear un método de ejecución de objetos de forma dinámica

Crear un método de ejecución de objetos de forma dinámica

Cree un objeto de la clase y llame al método NewInstance () del objeto Class

  • La clase debe tener un constructor sin parámetros.
  • Los derechos de acceso del constructor de la clase deben ser suficientes

Llamar al método especificado

A través de la reflexión, llame al método en la clase, complete a través de la clase Método.

  • Obtenga un objeto Method a través del método getMethod (String name, Class ... parameterTypes) de la clase Class y establezca los tipos de parámetros necesarios para el funcionamiento de este método.
  • Luego use la invocación de objeto (Object obj, Object [] args) para llamar y pasar la información del parámetro del objeto obj que se establecerá en el método

Invocación de objeto (Object obj, Object ... args)

  • El objeto corresponde al valor de retorno del método original. Si el método original no tiene un valor de retorno, devuelve un valor nulo en este momento.
  • Si el método original es un método estático, entonces el parámetro formal Object obj puede ser nulo
  • Si la lista de parámetros del método original está vacía, Object [] args es nulo
  • Si el método original es privado, debe llamar explícitamente al método setAccessible (true) del objeto de método antes de llamar a este método invoke () para acceder al método privado
package Reflection;

import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;

//动态创建对象,通过反射
public class Test08 {
    
    
    public static void main(String[] args) throws ClassNotFoundException, IllegalAccessException, InstantiationException, NoSuchMethodException, InvocationTargetException, NoSuchFieldException {
    
    
        //获得Class对象
        Class c1 = Class.forName("Reflection.User");

        //构造一个对象
//        User user = (User)c1.newInstance();  //本质是调用了类的无参构造器
//        System.out.println(user);

        //通过构造器创建对象
        Constructor con = c1.getDeclaredConstructor( int.class,String.class, int.class);
        User user11 = (User) con.newInstance(001, "XXX", 18);
        System.out.println(user11);


        //通过反射调用普通方法
        User u = (User)c1.newInstance();
        //通过反射获取一个方法
        Method setName = c1.getDeclaredMethod("setName", String.class);

        //invoke :激活的意思
        //(对象,"方法值")
        setName.invoke(u,"XXXXX");
        System.out.println(u.getName());


        //通过反射操作属性
        System.out.println("------------------------------");
        User u21=(User)c1.newInstance();
        Field name = c1.getDeclaredField("name");

        //不能直接操作私有属性,我们需要关闭程序权限的安全检测
        name.setAccessible(true);
        name.set(u21,"AAAAA");
        System.out.println(u21.getName());
    }
}

setAccessible

  • Los objetos Method y Field Constructor tienen el método SetAccessible ()
  • Cambie para habilitar y deshabilitar la verificación de seguridad de acceso cuando setAccessible esté en vigor
  • El valor del parámetro es verdadero, lo que indica que el objeto reflejado debe cancelar la verificación de acceso al lenguaje Java cuando esté en uso
    • Mejora la eficiencia de la reflexión. Si se debe usar la reflexión en el código, y el código debe llamarse con frecuencia, configure en Verdadero
    • Hacer que también se pueda acceder a miembros privados que de otro modo serían inaccesibles
  • El valor del parámetro es Falso, lo que indica que el objeto de reflexión debe implementar comprobaciones de acceso al lenguaje Java

Caso método común modo de reflexión y modo de reflexión velocidad de comparación de detección cerrada

package Reflection;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;

public class Test09 {
    
    


    //普通方法
    public static void test1(){
    
    
     User u=new User();
     long startTime=System.currentTimeMillis();

     for (int i = 0; i < 1000000000; i++) {
    
    
        u.getName();
     }
     long entTime=System.currentTimeMillis();
        System.out.println("时间为:"+(entTime-startTime)+"ms");
    }

    //反射方式调用
    public static void test2() throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {
    
    
        User u=new User();
        Class c1 = u.getClass();

        Method getName = c1.getDeclaredMethod("getName", null);

        long startTime=System.currentTimeMillis();

        for (int i = 0; i < 1000000000; i++) {
    
    
           getName.invoke(u,null);
        }
        long entTime=System.currentTimeMillis();
        System.out.println("时间为:"+(entTime-startTime)+"ms");
    }

    //反射方式调用  关闭检测
    public static void  test3() throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {
    
    
        User u=new User();
        Class c1 = u.getClass();

        Method getName = c1.getDeclaredMethod("getName", null);
        getName.setAccessible(true);
        long startTime=System.currentTimeMillis();

        for (int i = 0; i < 1000000000; i++) {
    
    
            getName.invoke(u,null);
        }
        long entTime=System.currentTimeMillis();
        System.out.println("时间为:"+(entTime-startTime)+"ms");
    }

    public static void main(String[] args) throws NoSuchMethodException, IllegalAccessException, InvocationTargetException {
    
    
        test1(); //10ms
        test2(); //4083ms
        test3(); //1649ms
    }

}

Supongo que te gusta

Origin blog.csdn.net/qq_45162683/article/details/112168558
Recomendado
Clasificación