javaSE (四十一)反射的概念、通过反射越过泛型检查

作为javaSE的最后一篇,反射更多的是一种编程理念或者说优化,对前面的java多态的一种优化,简单但是需要理解一下

这篇文章写的很好:
大白话说Java反射:入门、使用、原理


1、反射的概念:

  • 反射是相对于正射来说的,正射是先通过构造方法创建类的对象,然后使用类的各种属性和方法
  • 而反射是什么时候想要用到这个类了,就通过类名把这个类加载进来,然后获得构造方法,获得属性和方法,更加地可持续

方法:

获得类.class

大部分应用的是第一种,指导类名(完整的,包名+类名)可以和config配置文件结合起来
在这里插入图片描述

下面写一个代码包括以下的反射用法:

  1. 通过类名获得类
  2. 通过无参构造获得对象,需要从class向下转型
  3. 指定有参构造函数 ,参数都是字节码
  4. 用这个有参构造对象
  5. 获得字段(私有private属性)
  6. 去除私有权限
  7. 修改字段
  8. 获得无参方法
  9. 获得有参方法

实例代码:

package reflection;

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

public class Reflection {
	public static void main(String[] args) throws Exception {
		Class clazz = Class.forName("reflection.Student");//1、通过类名获得类
		Student  s = (Student) clazz.newInstance();//2、通过无参构造获得对象,需要从class向下转型
		
		Constructor con = clazz.getConstructor(String.class,int.class); //3、指定有参构造函数,参数都是字节码
		
		//T newInstance(Object... initargs)  
		
		Student str1 = (Student) con.newInstance("吴彦祖",23);  //4、用这个有参构造对象
		
		//Field field = clazz.getField("name");//5、获得字段(共有public属性)
		Field field = clazz.getDeclaredField("name");//5、获得字段(私有private属性)
		field.setAccessible(true);  //6、去除私有权限
	    field.set(str1, "PziAn");  //7、修改字段
	    System.out.println(str1);  //输出:Student [name=PziAn, age=23]
	    
	    //方法 getMethod(String name, 类<?>... parameterTypes)  
	    
	    Method method1 = clazz.getMethod("eat"); //8、获得无参方法
	    
	    method1.invoke(str1);  //输出:吃魷魚絲!
	    
	    
        Method method2 = clazz.getMethod("eat",int.class); //9、获得有参方法
	    
	    method2.invoke(str1,8);  //输出:吃魷魚絲8次!
		
		
	}

}

输出:

Student [name=PziAn, age=23]
吃魷魚絲
吃魷魚絲8次!

2、通过反射越过泛型检查:

泛型只是在编译阶段起作用,运行阶段会被擦除,所以我们在编译后拿到这个类的字节码,可以做一些事情,比如在ArrayList<Integer> 中放String类型的数

编译:将文件.java变成机器能识别的字节码.class

实例代码:

package reflection;

import java.lang.reflect.Method;
import java.util.ArrayList;

public class ArrayListwithreflection {

	public static void main(String[] args) throws Exception {
		ArrayList<Integer> list = new ArrayList<>();
		list.add(111);
		list.add(222);

		Class clazz = Class.forName("java.util.ArrayList");
		// 获得add方法

		Method method = clazz.getMethod("add", Object.class);// 注意这里是object

		method.invoke(list, "南京是一座很美的城市!");

		System.out.println(list);

	}

}
输出:

[111, 222, 南京是一座很美的城市!]

猜你喜欢

转载自blog.csdn.net/weixin_39782583/article/details/85015268
今日推荐