Java反射 类类型就是可以操作的类本身 如何通过反射得到函数 函数返回值 函数参数

Java反射的个人理解:反射就是一种 了解类并使用类 的一套方法;

学过Java基础的都知道如何进行类的实例化,也知道通过实例调用变量或者方法;
但很多时候类不是我们自己写的,所以我们对类不是很了解,这个时候可以通过反射来了解或者调用类本身。
假设有个类 名字是A

Class A{
}  

了解这个类我们可以用它创建变量,调用函数,但是当你不知道这个类,那么关于函数本身是不是无从下手,怎么办?
一切类是Class类的对象;Class c1=A.class所以我们的到的是一个等同于类本身的东西,如c1,官方名叫类类型(Class Type),通过c1可以对类A进行一系列操作;


深入了解,有人把类类型叫做字节码文件 很贴切;
因为反射只存在于在运行阶段,也就是在运行时,调用已经编译好的Class,比如Class c=A.class,可以理解为调用A已经编译好的类文件 A.class,所以与反射相关的所有参数都得是类类型,对应各个编译好的文件,比如利用反射调用注解 都得是XX.class,而且注解的生存周期必须是Runtime,这样运行时这些注解还存在

0.三种反射初始化

        Class c1=A.class;

        A a=new A();
        Class c2=a.getClass();

        try {
            Class c3=Class.forName("A");
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }

1. 创建实例;

通过

A a2=(A)c1.newInstance();

创建了A的实例a2,是不是通过类类型c1实现了和类A一样的实例化功能
那么我们得到了A类的替身c1,从而可以对类本身进行一系列操作,如类里面的函数,函数的返回值和参数值;

2. 方法

如下,A类中定义了3个函数,通过c1.getMethod我们得到了一类A中的
方法集合(Method[] methods);
方法返回值类类型(Class reType);
方法函数值类类型(Class[] paraTypes);
从而可以进一步调用函数
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;

/**
 * Created by XUH-h on 2017/7/19.
 */
public class SimpleTest {
    public static void main(String[] args) throws InvocationTargetException, IllegalAccessException {
        Class c1=A.class;

        try {

            Method m1=c1.getMethod("print", int.class, int.class);
            Method m2=c1.getMethod("print", new Class[]{String.class,String.class});
            m1.invoke(new A(),1,2);
            Method[] methods=c1.getDeclaredMethods(); //函数类类型数组
            for (Method method : methods
                    ) {

                System.out.println("METHOD: "+method.getName());

                Class reType = method.getReturnType();//函数返回值类类型
                System.out.println("   RETURN: "+reType.getName());

                Class[] paraTypes = method.getParameterTypes();//函数参数类类型数组
                for (Class paraType : paraTypes
                        ) {
                    System.out.println("   PARAMETER: "+paraType.getName());
                }

            }
        } catch (NoSuchMethodException e) {
            e.printStackTrace();
        }
    }
}
class A{
    public void print(int a,int b){
        System.out.println(a+b);
    }
    public void print(String a,String b){
        System.out.println(a.toUpperCase()+" "+b.toLowerCase());
    }
    public String print2(int a,int b){
        return  ""+a*b;
    }
}

运行结果,得到了A类中所有函数的返回值类型和参数类型,也可以调用A中的函数;

3
METHOD: print
   RETURN: void
   PARAMETER: java.lang.String
   PARAMETER: java.lang.String
METHOD: print
   RETURN: void
   PARAMETER: int
   PARAMETER: int
METHOD: print2
   RETURN: java.lang.String
   PARAMETER: int
   PARAMETER: int

因此我们看到,当你不了解类,或者不需要了解,只是调用的时候可以使用反射轻松达到;因而

类类型就是可以进行各种操作的类本身

另外一个作用是实现动态加载,
比如

Class.forName(args[0])

可以在编译后,运行时动态加载所需要的类
还比如jdbc与MySQL连接,

Class.forName("driver")

就使用了反射

猜你喜欢

转载自blog.csdn.net/evanxuhe/article/details/75420186
今日推荐