Java之反射机制

1. 概述

JAVA反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法;对于任意一个对象,都能够调用它的任意一个方法和属性;这种动态获取的信息以及动态调用对象的方法的功能称为java语言的反射机制。

2. 反射机制初探

首先我们做一下准备工作:

package com.myreflex;

public class Demo {
    private String str1;
    public String str2;
    
    private void fun1(){
        System.out.println("You call fun1");
    }
    public void fun2(){
        System.out.println("You call fun2");
    }
    
    public void fun3(int param1, String param2) {
        System.out.println("You call fun3 with param:"+param1+" and "+param2);
    }
    
    public Demo(int param1, String param2) {
        System.out.println("Consturctor with "+param1+","+param2);
    }
    
    public Demo() {
        System.out.println("Consturctor with no param");
    }
}

我们先创建一个测试类,其中包含了一个私有属性、一个公有属性、一个私有方法和一个公有方法。并为这个类准备了三个不同参数构方法。稍后我们要用到这个类。

(1)通过一个对象获取完整的包名和类名

package com.myreflex;

public class TestMain {
    
    public static void main(String[] args) {
        Demo demo = new Demo();
        // 通过一个对象获取完整的包名和类名
        System.out.println(demo.getClass().getName()); 
    }
    
}

打印结果为:    com.myreflex.Demo。

(2)实例化一个类

package com.myreflex;

public class TestMain {
    
    public static void main(String[] args) {
        Class<?> clazz;
        Demo demo = null;
        try {
            clazz = Class.forName("com.myreflex.Demo");
            demo = (Demo) clazz.newInstance(); //通过clazz.newInstance()来实例化Demo
        } catch (InstantiationException e) {
        } catch (IllegalAccessException e) {
        } catch (ClassNotFoundException e1) {
        }
        demo.fun2();
    }
    
}

打印结果为:  

Consturctor with no param
You call fun2

但是要注意:此种方法需要Demo拥有无参数的默认构造方法。

(3)获取类的属性

package com.myreflex;

import java.lang.reflect.Field;

public class TestMain {
    
    public static void main(String[] args) {
        Class<?> clazz;
        try {
            clazz = Class.forName("com.myreflex.Demo");
            Field[] fields;
            fields = clazz.getFields(); //获取类的所有属性(public)
            System.out.println("--------------getFields----------------");
            for (Field field : fields) {
                System.out.println(field.getType().getName());
                System.out.println(field.getName());
            }
            
            fields = clazz.getDeclaredFields(); //获取类的所有属性(public以及private)
            System.out.println("--------------getDeclaredFields----------------");
            for (Field field : fields) {
                System.out.println(field.getType().getName());
                System.out.println(field.getName());
            }
        } catch (Exception e) {
            
        }
    }
    
}

打印结果为:

--------------getFields----------------
java.lang.String
str2
--------------getDeclaredFields----------------
java.lang.String
str1
java.lang.String
str2

(4)获取类的方法

package com.myreflex;

import java.lang.reflect.Method;

public class TestMain {
    
    public static void main(String[] args) {
        Class<?> clazz;
        try {
            clazz = Class.forName("com.myreflex.Demo");
            Method[] methods;
            methods = clazz.getMethods(); 
            System.out.println("--------------getMethods----------------");
            for (Method method : methods) {
                System.out.println(method.getName());
            }
            
            methods = clazz.getDeclaredMethods(); 
              System.out.println("--------------getDeclaredMethods----------------");
            for (Method method : methods) {
                System.out.println(method.getName());
            }
        } catch (Exception e) {
            
        }
    }
}

打印结果为:

--------------getMethods----------------
fun2
fun3
wait
wait
wait
equals
toString
hashCode
getClass
notify
notifyAll
--------------getDeclaredMethods----------------
fun1
fun2
fun3

(5)获取方法的参数类型

package com.myreflex;

import java.lang.reflect.Method;

public class TestMain {
    
    public static void main(String[] args) {
        Class<?> clazz;
        try {
            clazz = Class.forName("com.myreflex.Demo");
            Method[] methods = clazz.getDeclaredMethods(); 
            for (Method method : methods) {
                System.out.println(method.getName()+"方法的参数类型有:");
                Class<?>[] paramClasses = method.getParameterTypes();
                for (Class<?> paramClass : paramClasses) {
                    System.out.println(paramClass.getName());
                }
            }
        } catch (Exception e) {
            
        }
    }
}

打印结果为:

fun1方法的参数类型有:
fun2方法的参数类型有:
fun3方法的参数类型有:
int
java.lang.String

(6)类方法的调用

package com.myreflex;

import java.lang.reflect.Method;

public class TestMain {
    public static void main(String[] args) {
        Class<?> clazz;
        try {
            clazz = Class.forName("com.myreflex.Demo");
            Method method2 = clazz.getDeclaredMethod("fun2"); // 获取fun2的方法
            Method method3 = clazz.getDeclaredMethod("fun3", int.class, String.class); // 获取fun3的方法
            Demo demo = (Demo) clazz.newInstance(); // 创建一个Demo的实例
            method2.invoke(demo); // 执行fun2
            method3.invoke(demo, 111, "aaa"); // 执行fun3
        } catch (Exception e) {
        }
    }
}

(7)获取父类

package com.myreflex;

public class TestMain {
    public static void main(String[] args) {
        Class<?> clazz;
        try {
            clazz = Class.forName("com.myreflex.Demo");
            clazz = clazz.getSuperclass();
            System.out.println(clazz.getName());
        } catch (Exception e) {
        }
    }
}

打印结果为:java.lang.Object。

(8)获取全部构造函数

package com.myreflex;

import java.lang.reflect.Constructor;

public class TestMain {
    public static void main(String[] args) {
        Class<?> clazz;
        try {
            clazz = Class.forName("com.myreflex.Demo");
            Constructor<?>[] cons = clazz.getConstructors();
            for (Constructor<?> constructor : cons) {
                System.out.println(constructor);
            }
        } catch (Exception e) {
        }
    }
}

打印结果为:

public com.myreflex.Demo()
public com.myreflex.Demo(int,java.lang.String)

(9)未完待续

…………………

posted @ 2016-02-28 20:32  柚子苹果果  阅读(473)  评论(0编辑  收藏  举报