反射

本文详细解析了Java反射机制的作用,介绍了相关类的定位(如Class、Method、Constructor和Field),展示了如何通过Class.forName获取类实例、配置文件加载、类路径操作、类加载器原理,以及实际应用示例。

1. 概念

1.1 反射机制的作用

通过java中的反射机制可以操作字节码文件,class文件

1.2 反射机制的相关类在哪个包下

java.lang.reflect.*

1.3 反射机制相关的重要类

java.lang.Class:代表字节码文件,代表一个类型,代表整个类

java.lang.reflect.Method:代表字节码中的方法字节码,代表类中的方法

java.lang.reflect.Constructor:代表字节码中的构造方法字节码,代表类中的静态方法

java.lang.reflect.Field:代表字节码中的属性字节码,代表类中成员变量

// Class
public class User{
    // Field
    private int no;
    // Constructor
    public User(){
    }
    public User(int no){
        this.no = no;
    }
    // Method
    public void setNo(int no){
        this.no = no;
    }
    public void getNo(){
        return this.no;
    }  
}

2. 使用

2.1 获取Class的三种方式

  1. Class.forName(String className)获取类

    Class c1 = Class.forName("java.lang.String");
    
  2. 通过任何一个对象的.getClass()方法获得Class

    String s = "hello";
    Class x = s.getClass();
    

    注意:上面c1 == x(双等号比较内存地址),指向同一个String类

    image-20210105211013756

  3. java中的任何一个类,都有个一个class属性,可以通过className.class获取其类

    Class y = String.class;
    

2.2 获取Class后可以做什么

  1. 配置文件读取类创建对象

    通过c.newInstance()方法可以获得其实例化对象,类似于new,注意:必须需要无参构造函数

    可以直接通过配置文件读取信息创建对象。

    import java.io.FileReader;
    import java.util.Properties;
    import java.lang.Class;
    
    public class ReflectTest{
    	public static void main(String[] args) throws Exception{
            // 读取配置文件
    		FileReader reader = new FileReader("classInfo.properties");
    		Properties pro = new Properties();
    		pro.load(reader);
    		reader.close();
            // 反射创建类
    		String className = pro.getProperty("className");
    		Class c = Class.forName(className);
    		System.out.println(c);
    		Object x = c.newInstance();
    		System.out.println(x);
    		
    	}
    } 
    
  2. 反射直接加载类的static方法:Class.forName(className)会导致类加载,并且加载static方法

2.3 类路径获取

  1. 获取文件绝对路径

    filename是以src为根的相对路径

    String path = Thread.currentThread().getContextClassLoader().getResource("fileName").getPath;
    
  2. 获取文件的流

    InputStream reader = Thread.curretnThread().getContextClassLoader()
        .getResourceAsStream("filename");
    
  3. 资源绑定器读取配置文件

    • 只能读取类路径src下的配置文件;
    • 只能读取properties文件;
    • filename不能加后缀.properties
    ResourceBundle bundle = ResourceBundle.getBundle("filename");
    String value = bundle.getString(key);
    

2.4 类加载器

2.4.1 什么是类加载器

专门负载加载类的命令/工具 ClassLoader

2.4.2 jdk中的类加载器
  1. 启动类加载器
  2. 扩展类加载器
  3. 应用类加载器
2.4.3 jvm类加载过程

首先通过“启动类加载器”加载rt.jar包中类,如java.lang.String;

若未找到,通过“扩展类加载器”加载ext中的jar包;

若未找到,通过“应用类加载器”加载classPath中的jar包;

双亲委派机制:启动类加载器:父;扩展类加载器:母。若都加载不到,则通过应用类加载器加载jar包。
t.jar包中类,如java.lang.String;

评论 2
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值