zoukankan      html  css  js  c++  java
  • Java反射机制

    理解反射之前,我们应当知道 .java 文件将会被编译成 .class 文件。JVM 中的类加载器会加载 .class,一般是在类第一次使用的时候加载,也可以用Class.forName("com.mysql.jdbc.Driver")这种方式提前将类加载到 JVM 中,该方法会返回一个 Class 对象。

    Java 反射机制在程序运行时,对于任意一个类,都能够知道这个类的所有属性和方法;对于任意一个对象,都能够调用它的任意一个方法和属性。这种 动态的获取信息 以及 动态调用对象的方法 的功能称为 java 的反射机制

    大白话说就是:反射要在运行时才知道操作哪个类,进而获得该类的完整构造,并调用对应的方法。

    与反射密切相关的是 java.lang.reflect 包,以及 Class 类。java.lang.reflect 类库主要包含以下三个类:

    1. Field :可以使用 get() 和 set() 方法读取和修改 Field 对象关联的字段;
    2. Method :可以使用 invoke() 方法调用与 Method 对象关联的方法;
    3. Constructor :可以用 Constructor 创建新的对象。

    如何使用反射获取对象

    1. 通过 Class.forName()类型.class对象.getClass()来获取 Class 对象
    2. 通过 Class 对象的 newInstance(),或者先获取构造器再用构造器调用 newInstance()
    3. 进一步获取它的属性、方法等信息

    获取 Class 对象

    第一种,使用 Class.forName 静态方法

    1
    
    Class clz = Class.forName("java.lang.String");
    

    第二种,通过 类名.class 的方式,只适合在编译前就知道操作的 Class

    1
    
    Class clz = String.class;
    

    第三种,通过对象.getClass()的方式

    1
    2
    
    String str = new String("Hello");
    Class clz = str.getClass();
    

    通过反射创建类对象

    通过反射创建类对象主要有两种方式:通过 Class 对象的 newInstance() 方法、通过 Constructor 对象的 newInstance() 方法。

    第一种:通过 Class 对象的 newInstance() 方法。

    1
    2
    
    Class clz = Apple.class;
    Apple apple = (Apple)clz.newInstance();
    

    第二种:通过 Constructor 对象的 newInstance() 方法

    1
    2
    3
    
    Class clz = Apple.class;
    Constructor constructor = clz.getConstructor();
    Apple apple = (Apple)constructor.newInstance();
    

    通过 Constructor 对象创建类对象可以选择特定构造方法,而通过 Class 对象则只能使用默认的无参数构造方法。下面的代码就调用了一个有参数的构造方法进行了类对象的初始化。

    1
    2
    3
    
    Class clz = Apple.class;
    Constructor constructor = clz.getConstructor(String.class, int.class);
    Apple apple = (Apple)constructor.newInstance("红富士", 15);
    

    通过反射获取类属性、方法、构造器等

    反射

    反射的优缺点

    优点

    可扩展性 : 应用程序可以利用全限定名创建可扩展对象的实例,来使用来自外部的用户自 定义类;

    类浏览器和可视化开发环境 : 一个类浏览器需要可以枚举类的成员。可视化开发环境(如 IDE)可以从利用反 射中可用的类型信息中受益,以帮助程序员编写正确的代码。

    调试器和测试工具 : 调试器需要能够检查一个类里的私有成员。测试工具可以利用反射来 自动地调用类里定义的可被发现的 API 定义,以确保一组测试中有较高的代码覆盖率。

    缺点

    尽管反射非常强大,但也不能滥用。如果一个功能可以不用反射完成,那么最好就不 用。在我们使用反射技术时,下面几条内容应该牢记于心。

    性能开销 : 反射涉及了动态类型的解析,所以 JVM 无法对这些代码进行优化。因此,反射操作的效率要比那些非反射操作低得多。我们应该避免在经常被执行的代码或对性能要 求很高的程序中使用反射。

    安全限制 : 使用反射技术要求程序必须在一个没有安全限制的环境中运行。如果一个程序必须在有安全限制的环境中运行,如 Applet,那么这就是个问题了。

    内部暴露 : 由于反射允许代码执行一些在正常情况下不被允许的操作(比如:访问私有的 属性和方法),所以使用反射可能会导致意料之外的副作用,这可能导致代码功能失调并 破坏可移植性。反射代码破坏了抽象性,因此当平台发生改变的时候,代码的行为就有可 能也随着变化。

    反射的用途及实现

    待补充

    参考资料

    Java 反射由浅入深 | 进阶必备

    深入解析Java反射(1) - 基础

    学习java应该如何理解反射?

    大白话说Java反射:入门、使用、原理

  • 相关阅读:
    powerDesigner生成Html及Word
    MySQL中information_schema是什么
    使用Navicat快速生成数据库字典
    SpringBoot学习:使用spring-boot-devtools进行热部署
    ajax 把返回结果作为参数传递
    application.properties详解 --springBoot配置文件
    intellij idea 无法启动或调试 spring-boot
    mybatis添加记录时返回主键id
    springboot form 提交集合 list
    表单提交之List集合
  • 原文地址:https://www.cnblogs.com/shuiyj/p/13185191.html
Copyright © 2011-2022 走看看