Home  >  Article  >  Java  >  A brief introduction to Java reflection (code example)

A brief introduction to Java reflection (code example)

不言
不言forward
2018-11-24 16:38:063230browse

This article brings you a brief introduction to Java reflection (code examples). It has certain reference value. Friends in need can refer to it. I hope it will be helpful to you. .

1. A brief introduction to Class

The Class class represents the classes and interfaces in the running Java application. An enumeration is a class, an annotation is an interface, and each array also belongs to a class that is reflected as a class object that is shared by all arrays with the same element type and dimensionality. The primitive Java types (boolean, byte, char, short, int, long, float, and double), and the keyword void are also represented as class objects.

Excerpted from the Chinese version of jdk1.8. You may not understand it at first. Now I will explain it sentence by sentence.

The first sentence: After a class is loaded, the JVM will create a Class object of the corresponding class in the memory.

Second sentence: Objects of the same type and arrays with the same dimension (regardless of length) share the same Class object in memory.

The third sentence: The above primitive types will also have a Class object in memory

package com.dingyu;

import org.junit.Test;

/**
 * Class的简单使用方法
 * 
 * @author 70241
 *
 */
public class ClassDemo {
    @Test
    public void classTest1() {
        try {
            Class class1 = Class.forName("com.dingyu.User");// 第一种获取Class对象的方法
            User user = new User();
            Class class2 = user.getClass();// 第二种获取Class对象的方法
            Class class3=User.class;//第三种获取Class对象的方法
            System.out.println("接下来判断到底同一类的不同对象的Class对象是不是同一个:"
                    + (class1.hashCode() == class2.hashCode()&&class1.hashCode() == class3.hashCode()));

        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
    }

    @Test
    public void classTest2() {
        String[] s1 = new String[10];
        String[] s2 = new String[30];
        String[][] s3 = new String[3][30];
        System.out.println(s1.getClass().hashCode()==s2.getClass().hashCode());
        System.out.println(s1.getClass().hashCode()==s3.getClass().hashCode());
        
    }
}

2.Class is a simple way to obtain the attributes, constructors, methods and annotations of a class

package com.dingyu;

import java.lang.annotation.Annotation;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;

import org.junit.Test;

/**
 * Class的简单用法
 * 
 * @author dingyu
 *
 */
public class ClassDemo02 {

    @Test
    public void usingClass() throws Exception {

        Class userClass = Class.forName("com.dingyu.User");

        // 获得类名
        System.out.println(userClass.getName());// 获得全类名
        System.out.println(userClass.getSimpleName());// 获得类名

        // 获得属性
        Field[] fields = userClass.getDeclaredFields();// 获得所有的属性
        for (Field field : fields) {
            System.out.println(field.getName());
        }

        System.out.println(userClass.getDeclaredField("id").getName());// 获得指定的属性

        // 获得方法
        Method[] methods = userClass.getDeclaredMethods();// 获得所有的方法
        for (Method method : methods) {
            System.out.println(method.getName());
        }
        Method method = userClass.getDeclaredMethod("setId", int.class);// 获得指定的方法,前面方法名,后面方法的参数
        System.out.println(method.getName());

        // 获得构造器
        Constructor[] constructors = userClass.getDeclaredConstructors();
        System.out.println(constructors.length);
        Constructor constructor = userClass.getDeclaredConstructor(int.class, String.class, int.class);// 获得指定的构造器,需要指定构造的参数
        System.out.println(constructor.getName());

        // 获得注解
        Annotation[] annotations = userClass.getAnnotations();
        for (Annotation annotation : annotations) {
            System.out.println(annotation);
        }
        // 指定注解名
        MyAnnotation annotation = (MyAnnotation)userClass.getDeclaredAnnotation(MyAnnotation.class);
        System.out.println(annotation);
    }
}

3.Class dynamically calls the constructor, methods and modify attributes

package com.dingyu;

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

import org.junit.Test;
/**
 * 使用反射动态的调用构造器,方法,修改属性 
 * @author 70241
 *
 */
public class ClassDemo03 {
    @Test
    @SuppressWarnings("all")
    public void usingClass() throws Exception {
        Class class1 = Class.forName("com.dingyu.User");
        
        //使用反射去调用构造器
        User user1 = (User) class1.newInstance();//调用的是无参的
        
        Constructor constructor = class1.getDeclaredConstructor(int.class,String.class,int.class);//获得有参的构造器
        User user2 = (User) constructor.newInstance(04,"dingyu",20);//动态生成对象
        
        //使用反射去调用方法
        Method methodSetId = class1.getDeclaredMethod("setId",int.class);
        methodSetId.invoke(user1, 02);//执行user1中的setId,后面是给的参数
        System.out.println(user1.getId());
        
        //使用反射去修改属性的值
        Field field = class1.getDeclaredField("age");
        field.setAccessible(true);//因为age是私有的,加上这句就表示这个属性不需要做安全检查
        field.set(user1, 20);
        System.out.println(field.get(user1));
        System.out.println(user1.getAge());
        
        
        
    }
}

4. Reflection to obtain the generic type of parameters or return values ​​

package com.dingyu;

import java.lang.reflect.Method;
import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;
import java.util.Map;
/**
 * 反射获得带泛型的参数或返回值里泛型的的类型
 * @author dingyu
 *
 */
public class ClassDemo04 {
    public void test01(Map<Integer, String> map, String s) {

    }

    public Map<Integer, String> test02() {
        return null;
    }

    public static void main(String[] args) throws Exception {
        //参数中带泛型的
        Method method = ClassDemo04.class.getDeclaredMethod("test01", Map.class, String.class);
        Type[] types = method.getGenericParameterTypes();// 返回一个 Type对象的数组, Type以声明顺序表示由该对象表示的可执行文件的形式参数类型
        // 打印这些参数的类型
        for (Type type : types) {
            System.out.println(type.getTypeName());
            if (type instanceof ParameterizedType) {// 如果是泛型的参数
                Type[] actualTypeArguments = ((ParameterizedType) type).getActualTypeArguments();// 获得泛型的的类型
                for (Type type2 : actualTypeArguments) {
                    System.out.println(type2.getTypeName());
                }
            }
        }
        
        //返回值中带泛型的
        Method method02 = ClassDemo04.class.getDeclaredMethod("test02");
        Type type = method02.getGenericReturnType();// 返回的类型
        // 打印这些返回的类型            
        System.out.println(type.getTypeName());
        if (type instanceof ParameterizedType) {// 如果是泛型的参数
            Type[] actualTypeArguments = ((ParameterizedType) type).getActualTypeArguments();// 获得泛型的的类型
            for (Type type2 : actualTypeArguments) {
            System.out.println(type2.getTypeName());
            }
        }            
    }

}

The above is the detailed content of A brief introduction to Java reflection (code example). For more information, please follow other related articles on the PHP Chinese website!

Statement:
This article is reproduced at:cnblogs.com. If there is any infringement, please contact admin@php.cn delete