JAVA安全|基础篇:反射机制之快速入门

admin 2023年2月4日06:37:34评论53 views字数 2783阅读9分16秒阅读模式

0x00  前言

    JAVA安全系列文章主要为了回顾之前学过的java知识,构建自己的java知识体系,并实际地将java用起来,达到熟练掌握java编程,并能用java编写工具的目的。此系列文章需要读者具备一定java基础,不定时更新。相关详情可通过我的公众号文章进行查看:

JAVA安全|即将开启:java安全系列文章

    反射部分文章内容,主要来自B站韩顺平老师JAVA基础课的反射讲解部分,链接:

https://www.bilibili.com/video/BV1fh411y7R8?p=711&vd_source=f50eede57052ba3346254570c978a2ee

本文为JAVA安全系列文章第三篇。


0x01  引出反射机制(为什么和是什么)

1.为什么需要反射机制  

现有如下需求:

根据配置文件re.properties指定信息,创建Cat类并调用其hi方法。

JAVA安全|基础篇:反射机制之快速入门

JAVA安全|基础篇:反射机制之快速入门

按照传统方法,我们会先创建Properties对象去读取re.properties里的classfullpath和method字段,然后读取到类路径new一个对象出来,再调用其方法,但我们读取到的是一个字符串,无法创建对象呀:

JAVA安全|基础篇:反射机制之快速入门

注:这种通过外部配置文件,在不修改源码的情况下来控制程序的需求,在框架中应用很多。符合设计模式中的ocp(Open-Closed Principle)原则,即不修改源码(开),扩容功能(闭)。

既然传统方法不能解决,那我们就需要学习新的技术方法—反射机制来解决了:

JAVA安全|基础篇:反射机制之快速入门

注:此处若要调用Cat类的cry()方法,只需修改配置文件,无需修改源码

初次接触看不懂?加载类?Class类型的对象?方法也可以是对象?看完下面再回过来看,这些问题都能明白了。


2.反射机制概念

反射机制允许程序在执行期间借助于ReflectionAPI取得任何类的内部信息(比如成员变量,构造器,成员方法等),并能操作对象的属性及方法。通过反射机制我们可以完成:

(1)在运行时判断任意一个对象所属的类

(2)在运行时构造任意一个类的对象

(3)在运行时得到任意一个类所具有的成员变量和方法

(4)在运行时调用任意一个对象的成员变量和方法

(5)生成动态代理

网上大多讲反射的文章,基本都是放上上面一段文字,然后介绍一些API,再来几段代码示例一下,导致看了其实还不是太能理解反射。下面会从原理上来介绍反射。


0x02  反射机制原理

我们的Java程序在计算机中有三个阶段:

1.第一阶段:代码阶段/编译阶段

最开始学习java时,我们都会创建一个.java后缀的文件,然后在里面写上我们的代码。运行前通过javac对其进行编译,得到一个.class后缀的字节码文件


2.第二阶段:类加载阶段(Class类阶段)

当执行new一个对象时,会先通过类加载器ClassLoader将我们所需要的类进行加载(此处就体现了反射),这里的类加载是以.class后缀文件为基础的。加载完后,在堆中会产生一个Class类型的对象(一个类只有一个Class对象),这个对象包含了类的完整结构信息(成员变量、构造器、成员方法等),通过这个对象得到类的结构。(Class对象就像是一面镜子,透过这个镜子看到类的结构,故形象的称之为反射)


3.第三阶段:Runtime运行阶段

在运行阶段,我们通过new的方式创建的对象是在堆中,该对象知道它是属于哪个Class对象。若我们得到Class对象,也同样可以通过它来创建对象,调用对象方法,操作属性等。

反射机制原理可以用下图示意:

JAVA安全|基础篇:反射机制之快速入门


0x03  与反射相关的主要类

java中与反射相关的类主要有四个:

  1. java.lang.Class

    代表一个类,Class对象表示某个类加载后在堆中的对象

  2. java.lang.reflect.Method

    代表类的方法,Method对象表示某个类的方法

  3. java.lang.reflect.Field

    代表类的成员变量,Field对象表示某个类的成员变量

  4. java.lang.reflect.Constructor

    代表类的构造方法,Constructor对象表示构造器

通过上面的介绍,可以发现在反射中,成员方法,成员变量,构造器这些均为对象,将Java语言"万物皆对象"的特点表现得淋漓尽致。

这些类中每个类都继承了一些类,实现了一些接口,故每个类都会有很多方法,这些方法有自身的,有父类的,有接口的。拿java.lang.reflect.Method来说,类图是这样的:

JAVA安全|基础篇:反射机制之快速入门
其可调用的方法有很多:

JAVA安全|基础篇:反射机制之快速入门

使用方法其实都是调用API,我们掌握一些常用的就行,重点在于理解反射的原理。下面是快速入门示例代码:

Cat类:

JAVA安全|基础篇:反射机制之快速入门

Reflection01类:

JAVA安全|基础篇:反射机制之快速入门

运行效果:

JAVA安全|基础篇:反射机制之快速入门从示例代码中可以看出,方法对象,属性对象,构造器对象都是通过调用Class对象的API来获取的,而后要调用方法、获取属性值、通过构造器去创建对象实例等使用相应对象的API即可。由此可见Class类在反射机制中占有重要地位。


0x04   反射优缺点及优化

  1. 优点

    通过反射我们可以动态创建和使用对象,使用灵活,没有限制。反射机制是框架的灵魂,底层框架的核心,反射机制使得Java能成为一种动态语言。没有反射也就没有框架,Java语言也就成为不了天下第一(狗头)


2.缺点

使用反射基本就是解释执行,对执行速度有影响。


3.反射优化—关闭访问检查

Method、Field、Constructor对象都有setAccessible()方法,其作用是启动和禁用访问安全检查的开关。参数值为true表示反射的对象在使用时取消访问检查,提高反射的效率。参数值为false则表示反射的对象执行访问检查。

具体参看下面代码:

JAVA安全|基础篇:反射机制之快速入门

我将上面的代码执行了三轮,结果记录如下:

JAVA安全|基础篇:反射机制之快速入门

注:三个方法应分开单独执行。若执行完了第一个方法再去执行第二个方法,那么在第二个方法里创建对象的时间会被缩短,对结果会造成影响,因为类只会被加载一次,每个类在堆中只会有一个Class对象。

由上面的实验结果我们可以得出结论:

(1)当我们创建对象并调用其方法时,传统方法要比使用反射更快

(2)关闭访问安全检查可以使得反射的运行速度快一丢丢。


0x05   总结

    本文先通过一个例子来引出反射机制,再介绍了反射概念及作用,然后介绍反射机制的原理(重点),反射相关的四个主要类,反射优缺点及优化,达到了一个快速入门的目的。需掌握的知识点:

  1. 反射机制的概念、原理、作用

  2. 反射相关的四个主要类的API的基本使用

  3. 关闭访问安全检查可以使得反射的运行速度快一丢丢

可能有读者还不太理解Class类到底是什么,这也是反射机制的重点内容,下一篇文章将重点介绍Class类


如果喜欢小编的文章,记得多多转发,点赞+关注支持一下哦~,您的点赞和支持是我最大的动力~


原文始发于微信公众号(沃克学安全):JAVA安全|基础篇:反射机制之快速入门

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2023年2月4日06:37:34
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   JAVA安全|基础篇:反射机制之快速入门https://cn-sec.com/archives/1284227.html

发表评论

匿名网友 填写信息