【Java動態性】之反射機制 reflection

1、Java反射機制簡介java

      1. 指的是能夠於運行時加載、探知、使用編譯期間徹底未知到類;數組

      2. 程序在運行狀態中,能夠動態加載一個只有名稱到類,對於任意一個已加載的類,都可以知道這個類的全部屬性和方法;對於任意一個對象,都可以調用它都任意一個方法和屬性;對象

      3. 加載完類以後,在堆內存中,就產生一個Class類型都對象(一個類只有一個Class對象),這個對象就包含了完整都類都結構信息。能夠經過這個對象看到類的結構。這個對象就像一面鏡子,透過這個鏡子看到類的結構,因此形象的稱之爲:反射。內存

      4. Class類介紹:java.lang.Class類十分特殊,用來表示java中類型【class | interface | enum | annotation | primitive type | void 】自己;Class類的對象包含了某個被加載類的結構;一個被加載的類對應一個Class對象;當一個class被加載,或當加載器(class loader)的defineClasss()被JVM調用,JVM便自動產生一個Class對象;Class類是Reflection的根源;針對任何你想動態加載、運行的類、惟有先得到相應的Class對象。get

      5. Class類對象獲取方式:1)對象.getClass(); 2)Class.forName("路徑");3)類名.class。hash

      6. 反射機制經常使用做用:1)動態加載類、動態獲取類的信息(屬性、方法、構造器);2)動態構造對象;3)動態調用類和對象的任意方法、構造器;4)動態調用和處理屬性;5)獲取泛型信息;6)處理註解。it

2、io

public class Demo01 {

    public static void main(String[] args) {
        String path = "com.mimidai.test.User";
        try {
            Class clazz = Class.forName(path);
            System.out.println("clazz.hashCode()= " + clazz.hashCode());
            Class clazz2 = Class.forName(path);
            System.out.println("clazz2.hashCode()=" + clazz2.hashCode());
            /**
             * 一個類只有一個Class對象
             */
            System.out.println(clazz.hashCode() == clazz2.hashCode());
            /**
             * Class對象獲取方式
             */
            Class strClazz = String.class;
            Class strClazz2 = path.getClass();
            System.out.println(strClazz == strClazz2);
            /**
             *  Class對象獲取跟數組維度有關
             */
            Class intClazz = int.class;
            int[] arr01 = new int[10];
            int[][] arr02 = new int[30][3];
            int[] arr03 = new int[30];
            double[] arr04 = new double[10];
            System.out.println("intClazz.hashCode()=" + intClazz.hashCode());
            System.out.println("arr01.getClass().hashCode()=" + arr01.getClass().hashCode());
            System.out.println("arr02.getClass().hashCode()=" + arr02.getClass().hashCode());
            System.out.println("arr03.getClass().hashCode()=" + arr03.getClass().hashCode());
            System.out.println("arr04.getClass().hashCode()=" + arr04.getClass().hashCode());
        } catch(Exception e) {
            e.printStackTrace();
        }
    }
}
public class Demo02 {
    public static void main(String[] args) {
        String path = "com.mimidai.test.User";
        try {
            Class clazz = Class.forName(path);
            /**
             * 獲取類的名字
             */
            System.out.println("clazz.getSimpleName(): " + clazz.getSimpleName());
            System.out.println("clazz.getName(): " + clazz.getName());
            /**
             * 獲取屬性信息
             */
            Field[] fields = clazz.getFields();
            System.out.println("fields.length= " + fields.length);
            for (Field f : fields) {
                System.out.println("屬性:" + f);
            }
            Field[] fields2 = clazz.getDeclaredFields();
            System.out.println("fields2.length" + fields2.length);
            for (Field f : fields2) {
                System.out.println("屬性:" + f);
            }
            /**
             * 獲取方法信息
             */
            Method[] methods = clazz.getDeclaredMethods();
            for (Method m : methods) {
                System.out.println("方法:" + m);
            }
            Method m01 = clazz.getDeclaredMethod("getName", null);
            Method m02 = clazz.getDeclaredMethod("setName", String.class);
            System.out.println("m01: " + m01);
            System.out.println("m02: " + m02);
            /**
             * 獲取構造器信息
             */
            Constructor[] constructors = clazz.getDeclaredConstructors();
            for (Constructor constructor : constructors) {
                System.out.println("構造器:" + constructor);
            }
            Constructor constructor = clazz.getDeclaredConstructor(Long.class, String.class, Integer.class);
            System.out.println("constructor: " + constructor);

            Class<User> c = (Class<User>)Class.forName(path);
            /**
             * 經過反射API調用構造方法、構造對象
             * 1. 默認調用了User的無參構造方法
             */
            User user = c.newInstance();
            System.out.println(user);
            Constructor<User> constructor1 = c.getDeclaredConstructor(Long.class, String.class, Integer.class);
            User user2 = constructor1.newInstance(100L, "張三", 19);
            System.out.println("user2.getName(): " + user2.getName());
            /**
             * 經過反射API調用普通方法
             */
            User user3 = c.newInstance();
            Method method = c.getDeclaredMethod("setName", String.class);
            method.invoke(user3, "哈哈");
            System.out.println("user3.getName(): " + user3.getName());
            /**
             * 經過反射API操做屬性
             */
            User user4 = c.newInstance();
            Field field = c.getDeclaredField("name");
            field.setAccessible(true);
            field.set(user4, "呵呵");
            System.out.println("user4.getName(): " + user4.getName());
            System.out.println("field.get(user4): " + field.get(user4));

        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}
/**
 * 經過反射獲取泛型信息
 */
public class Demo03 {

    public void test01(Map<String, User> map, List<User> list) {
        System.out.println("Demo03.test01");
    }
    public Map<Integer, User> test02() {
        System.out.println("Demo03.test02");
        return null;
    }
    public static void main(String[] args) {
        try {
            /**
             * 獲取指定方法參數泛型信息
             */
            Method method = Demo03.class.getMethod("test01", Map.class, List.class);
            Type[] types = method.getGenericParameterTypes();
            for (Type type : types) {
                System.out.println("##" + type);
                if (type instanceof ParameterizedType) {
                    Type[] genericTypes = ((ParameterizedType)type).getActualTypeArguments();
                    for (Type genericType : genericTypes) {
                        System.out.println("泛型類型:" + genericType);
                    }
                }
            }

            /**
             * 獲取指定方法返回值泛型信息
             */
            Method method1 = Demo03.class.getMethod("test02", null);
            Type returnType = method1.getGenericReturnType();
            if (returnType instanceof ParameterizedType) {
                Type[] genericTypes = ((ParameterizedType)returnType).getActualTypeArguments();
                for (Type genericType : genericTypes) {
                    System.out.println("返回值,泛型類型:" + genericType);
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}
相關文章
相關標籤/搜索