Java反射01 反射_Class 反射_Method Annotation

来源:互联网 发布:微信打印机软件 编辑:程序博客网 时间:2024/06/03 02:32

工程截图:



反射操作类:

package com.jp.reflect;import java.io.InputStream;import java.lang.annotation.Annotation;import java.lang.reflect.Field;import java.lang.reflect.InvocationTargetException;import java.lang.reflect.Method;import org.junit.Test;public class ReflectionTest {/** * Annotation 和 反射 * 1、获取Annotation  *  * getAnnotation getDeclaredAnnotations *  * @throws Exception */@Testpublic void testAnnotation() throws Exception {String className = "com.jp.reflect.Person";Class clazz = Class.forName(className);Object obj = clazz.newInstance();Method method = clazz.getDeclaredMethod("setAge", Integer.class);int val = 138;Annotation annotation = method.getAnnotation(AgeValidator.class);if (annotation != null) {if (annotation instanceof AgeValidator) {AgeValidator ageValidator = (AgeValidator) annotation;if (val < ageValidator.min() || val > ageValidator.max()) {throw new RuntimeException("年龄非法");}}}method.invoke(obj, 51);System.out.println(obj);}/** * @param obj *            :某一类的一对象 * @param methodName *            : 类的一个方法的方法名,该方法可能是私有方法,还可能是该方法在父类中定义的私有方法 * @param args *            : 调用的方法需要传入的参数 * @return 调用方法后的返回值 */public Object invoke2(Object obj, String methodName, Object... args) {// 1.获取Method对象Class[] parameterTypes = new Class[args.length];for (int i = 0; i < parameterTypes.length; i++) {parameterTypes[i] = args[i].getClass();}try {// 2.执行Method方法// 3.返回方法的返回值Method method = obj.getClass().getDeclaredMethod(methodName,parameterTypes);return method.invoke(obj, args);} catch (Exception e) {e.printStackTrace();}return null;}/** * 获取clazz的methodName 方法,该方法可能是私有方法,还可能在父类中(私有方法) *  * @param clazz * @param methodName * @param parameterTypes * @return */public Method getMethod(Class clazz, String methodName,Class... parameterTypes) {for (; clazz != Object.class; clazz = clazz.getSuperclass()) {try {Method method = clazz.getDeclaredMethod(methodName,parameterTypes);return method;} catch (Exception e) {e.printStackTrace();}}return null;}public void testGetMethod() throws ClassNotFoundException {Class clazz = Class.forName("com.jp.reflect.Student");Method method = getMethod(clazz, "method1", Integer.class);System.out.println(method);// method = getMethod(clazz, "method2");// System.out.println(method);}public void testInvoke2() {Object obj = new Student();// Student 类的method1()方法被调用,打印"private void method1"invoke2(obj, "method1", 10);// Student 类的父类的method2()方法被调用,返回值为"private String method2"Object result = invoke2(obj, "method2");System.out.println(result);}/** * 若通过 Method 的invoke() 方法调用方法,而访问权限不足,则可以先使该方法变为可被 访问的方法。 *  * @throws NoSuchMethodException * @throws SecurityException * @throws IllegalAccessException * @throws IllegalArgumentException * @throws InvocationTargetException */public void testInvokePrivateMethod() throws NoSuchMethodException,SecurityException, IllegalAccessException,IllegalArgumentException, InvocationTargetException {Object obj = new Student();Class clazz = obj.getClass();Method method = clazz.getDeclaredMethod("method1", Integer.class);System.out.println(method);// 若血药通过反射执行私有方法method.setAccessible(true);method.invoke(obj, 10);}/** * 获取当前类的父类: 直接调用Class 对象的getSuperclass() 方法 *  * @throws ClassNotFoundException *  */public void testGetSuperClass() throws ClassNotFoundException {String className = "com.jp.reflect.Student";Class clazz = Class.forName(className);Class superClazz = clazz.getSuperclass();System.out.println(superClazz);}/** * @param className *            : 某个类的全类名 * @param methodName *            : 类的一个方法的方法名 * @param args *            : 调用的方法需要传入的参数 * @return 调用方法后的返回值 */public Object invoke(String className, String methodName, Object... args) {Object obj = null;try {obj = Class.forName(className).newInstance();return invoke(obj, methodName, args);} catch (Exception e) {e.printStackTrace();}return null;}/** * @param obj *            : 执行方法的对象 * @param methodName *            : 类的一个方法的方法名,该方法可能是私有方法 * @param args *            : 调用的方法需要传入的参数 * @return 调用方法后的返回值 */public Object invoke(Object obj, String methodName, Object... args) {// 1.获取Method对象Class[] parameterTypes = new Class[args.length];for (int i = 0; i < parameterTypes.length; i++) {parameterTypes[i] = args[i].getClass();}try {// 2.执行Method方法// 3.返回方法的返回值Method method = obj.getClass().getDeclaredMethod(methodName,parameterTypes);return method.invoke(obj, args);} catch (Exception e) {e.printStackTrace();}return null;}public void testInvoke() {Object obj = new Person();invoke(obj, "setName", "Jason", new Integer(1));invoke("com.jp.reflect.Person", "setName", "Jason", new Integer(12));// Object result = invoke("java.text.SimpleDateFormat", "format",// new Date());// System.out.println(result);}/** * Class 是对一个类的描述 类的属性: Field 类的方法:Method 类的构造器:Constructor *  * Method:对应类中的方法。 *  * 1、获取Method *  * 1.1、获取类的数组:clazz.getDeclaredMethods *  * 1.2获取类的指定的方法:clazz.getDeclaredMethod(String name, Class<?>... * parameterTypes) *  * 1.3通过Method对象执行方法: method.invoke(Object obj, Object... args) obj执行那个对象的方法 *  */public void testMethod() throws Exception {Class clazz = Class.forName("com.jp.reflect.Person");// 1.得到clazz对应的类中有哪些方法,不能获取private方法Method[] methods = clazz.getMethods();for (Method method : methods) {System.out.println("^" + method.getName());}// 2.获取所有的方法,包括private方法,且至获取当前类声明的方法Method[] methods2 = clazz.getDeclaredMethods();for (Method method : methods2) {System.out.println("~" + method.getName());}// 3.获取指定的方法(指定参数)。Method method = clazz.getDeclaredMethod("setName", String.class);System.out.println(method);method = clazz.getDeclaredMethod("test");System.out.println(method);method = clazz.getDeclaredMethod("setName", String.class, Integer.class);System.out.println(method);// 4.执行方法Object obj = clazz.newInstance();method.invoke(obj, "jack", 12);// 参数1 执行那个对象的方法}public void testClassLoader() throws ClassNotFoundException {// 1.获取一个系统的类加载器ClassLoader classLoader = ClassLoader.getSystemClassLoader();System.out.println(classLoader);// 2.获取系统类加载器的父类加载器classLoader = classLoader.getParent();System.out.println(classLoader);// 3.获取扩展类加载器的父类加载器classLoader = classLoader.getParent();System.out.println(classLoader);// 4.测试当前类是由那个类加载器进行加载的classLoader = Class.forName("com.jp.reflect.ReflectionTest").getClassLoader();System.out.println(classLoader);// 引导类加载器,无法直接获取,打印null// 5.测试JDK提供的Object类有哪个类加载器负责加载classLoader = Class.forName("java.lang.Object").getClassLoader();System.out.println(classLoader);// 6.关于类加载器的一个主要方法。// 调用getResourceAsStream方法 获取类路径下文件对应的数据流// this.getClass().getClassLoader()系统加载器InputStream in = this.getClass().getClassLoader().getResourceAsStream("com/jp/reflect/test.properties");System.out.println(in);// new FileInputStream("test.properties");}/** * Class类的newInstance()方法 *  * @throws ClassNotFoundException * @throws IllegalAccessException * @throws InstantiationException */public void testNewInstance() throws ClassNotFoundException,InstantiationException, IllegalAccessException {String className = "com.jp.reflect.Person";Class clazz = Class.forName(className);// 利用Class 对象的newInstance()方法创建类的一个实例// 调用类的无参构造器// 一般的,一个类若声明了带参数的构造器,也要声明一个无参数的构造器Object obj = clazz.newInstance();System.out.println(obj);}/** * 关于Class: *  * 1、Class是一个类 *  * 2、对像照镜子后可以得到的信息,类名、属性、方法、实现接口,继承父类 *  * 一个类在JVM中只有一个Class实例 *  * @throws ClassNotFoundException *  */public void testClass() throws ClassNotFoundException {Class clazz = null;// 1、得到Class 对象// 1.1直接通过 类名.class 的方式得到clazz = Person.class;Field[] fields = clazz.getDeclaredFields();// 1.2通过对象调用getClass()方法来获取Object obj = new Person();clazz = obj.getClass();// 1.3通过类的全类名获取String className = "com.jp.reflect.Person";clazz = Class.forName(className);}}






package com.jp.reflect;public class Person {String name;Integer age;public Person(String name, int age) {super();this.name = name;this.age = age;System.out.println("有参数构造器");}public Person() {// 留给反射使用super();System.out.println("无参数构造器");}private void test() {}public String getName() {return name;}public void setName(String name, Integer age) {System.out.println("name:" + name);System.out.println("age:" + age);}public void setName(String name) {this.name = name;}public int getAge() {return age;}@AgeValidator(min = 18, max = 35)public void setAge(Integer age) {this.age = age;}private String method2() {return "private String method2";}@Overridepublic String toString() {return "Person [name=" + name + ", age=" + age + "]";}}


package com.jp.reflect;import java.lang.annotation.ElementType;import java.lang.annotation.Retention;import java.lang.annotation.RetentionPolicy;import java.lang.annotation.Target;@Retention(RetentionPolicy.RUNTIME)@Target(value = { ElementType.METHOD })public @interface AgeValidator {public int max();public int min();}



0 0
原创粉丝点击