Java反射基础学习笔记

Java反射基础知识

  • 一、Java反射的理解
  • 二、Java反射的知识
    • 1、如何获取Class类
    • 2、使用Class中的构造方法
    • 3、使用Class中的方法
    • 4、使用Class中的属性
    • 5、使用Class中的注解
    • 6、Class中的常用方法

Java反射要学习哪些内容,其实要知道的东西很少,也很简单掌握。主要如下:
第一部分就是要理解什么是反射。只需要知道反射可以获取 类的全部信息,其主要也是用来获取 类的全部信息
第二就是会使用反射。包括如何获取反射类、构造函数、成员变量、成员函数、注解等,以及一些常用方法的使用。

一、Java反射的理解

在不知道一个类的信息时,如何获取其中全部的方法呢?
反射就可以获取其中的全部方法的。
反射通过一系列复杂的方法获取了类的信息。
复杂方法是啥?别着急知道,初接触反射也不需要知道,先学会用,会用就行。
面向面试编程,后续再聊!

二、Java反射的知识

1、如何获取Class类

反射的使用要先有Class类,先要知道如何获取Class类

  • 通过实例化的对象获取

    MyClass myClass = new MyClass();
    Class<?> aClass = myClass.getClass();

  • 通过"类.class"获取

    Class<?> aClass = MyClass.class;

  • 通过类所在的包名获取

    Class<?> aClass = Class.forName(“packageName”);

public class Test1 {public static void main(String[] args) throws Exception {Object o = new Object();Class<?> aClass1 = o.getClass();Class<Object> aClass2 = Object.class;Class<?> aClass3 = Class.forName("java.lang.Object");System.out.println(aClass1);System.out.println(aClass2);System.out.println(aClass3);//输出均为"class java.lang.Object"}
}

2、使用Class中的构造方法

知道如何获取反射类的Class后,后面就要探讨怎么用了。先看看怎么通过反射实例化对象。

  • 先创建一个简单的类

    下面的类定义了四个构造函数,后续通过这四个构造函数进行实例化

    public class Apple {String color;int weight;public Apple() {}public Apple(String color, int weight) {this.color = color;this.weight = weight;}private Apple(int weight) {this.weight = weight;}private Apple(String color) {this.color = color;}
    }
    
  • 使用构造函数

    获取构造函数有2*2种方法:
    获取单个公共构造函数,获取全部公共构造函数,获取单个构造函数(私有也可以),获取全部构造函数(包括私有)。
    构造函数获取后就是实例化了,使用newInstace()方法来实例化,也传入对应的参数。

    import java.lang.reflect.Constructor;
    public class AppleTest {public static void main(String[] args) throws Exception {Class<Apple> aClass = Apple.class;//获取构造函数//获取构造函数的目的是为了能够进行反射创建实例Constructor<?> constructor1 = aClass.getConstructor();//其中的参数就是要获取的实例Object constructorObject1 = constructor1.newInstance(); //获取到构造函数进行新建System.out.println(constructorObject1);Constructor<?> constructor2 = aClass.getConstructor(String.class, int.class);Object constructorObject2 = constructor2.newInstance("red", 22); //获取到构造函数进行新建System.out.println(constructorObject2);//私有的方法是获取不到的。报错java.lang.NoSuchMethodException//Constructor<MyClass> constructor2 = aClass.getConstructor(String.class, int.class, int.class);//可以通过如下方式来取私有构造函数Constructor<?> declaredConstructor1 = aClass.getDeclaredConstructor(String.class);declaredConstructor1.setAccessible(true); //强行创建,否则会出现java.lang.IllegalAccessExceptionObject declaredConstructorObject1 = declaredConstructor1.newInstance("red");System.out.println(declaredConstructorObject1);Constructor<?> declaredConstructor2 = aClass.getDeclaredConstructor(int.class);declaredConstructor2.setAccessible(true); //强行创建,否则会出现java.lang.IllegalAccessExceptionObject declaredConstructorObject2 = declaredConstructor2.newInstance(22);System.out.println(declaredConstructorObject2);//关于构造函数对象的方法 getName() 获取方法名//获取全部的构造函数for (Constructor<?> declaredConstructor : aClass.getDeclaredConstructors()) {System.out.println("declaredConstructor:" + declaredConstructor);}}
    }
    
  • 输出结果

    Apple{color='null', weight=0}
    Apple{color='red', weight=22}
    Apple{color='red', weight=0}
    Apple{color='null', weight=22}
    declaredConstructor:private com.universe.test1.Apple(java.lang.String)
    declaredConstructor:private com.universe.test1.Apple(int)
    declaredConstructor:public com.universe.test1.Apple(java.lang.String,int)
    declaredConstructor:public com.universe.test1.Apple()
    

3、使用Class中的方法

获取成员方法有2*2种:
获取单个公共的方法,获取全部公共的方法,获取单个方法(包含私有),获取全部方法(包含私有)
获取成员方法有什么用呢?当然是为了用了,那么要怎么使用呢?invoke方法

  • 创建一个简单的类

    public class Util {//定义公共和私有的方法public void getPublicFun() {System.out.println("Util公共方法");}public String getPublicFun(String desc) {System.out.println("Util公共方法:" + desc);return desc;}private void getPrivateFun() {System.out.println("Util私有方法");}private String getPrivateFun(String desc) {System.out.println("Util私有方法:" + desc);return desc;}
    }
    
  • 通过反射使用方法

    import java.lang.reflect.Method;
    import java.util.Arrays;public class UtilTest {public static void main(String[] args) throws Exception {Class<Util> aClass = Util.class;//获取成员方法有2*2种。获取单个公共的方法,获取全部公共的方法,获取单个方法(包含私有),获取全部方法(包含私有)//获取成员方法有什么用呢?当然是为了用了,那么要怎么使用呢?invoke方法System.out.println("1、获取成员方法 Method");Util utilObject = aClass.getConstructor().newInstance();Method method1 = aClass.getMethod("getPublicFun");method1.invoke(utilObject);Method method2 = aClass.getMethod("getPublicFun",String.class);String method2return = (String) method2.invoke(utilObject,"公共方法赋值");System.out.println("method2return:"+method2return);System.out.println("2、私有成员方法的获取");//私有成员函数使用getMethod是获取不到的,报错java.lang.NoSuchMethodException//Method method2 = aClass.getMethod("getPrivateFun", String.class); //报错java.lang.NoSuchMethodException//私有成员方法通过getDeclaredMethod()获取Method declaredMethod1 = aClass.getDeclaredMethod("getPrivateFun");declaredMethod1.setAccessible(true); //私有直接赋值报错,需要开启权限。java.lang.IllegalAccessExceptiondeclaredMethod1.invoke(utilObject);Method declaredMethod2 = aClass.getDeclaredMethod("getPrivateFun", String.class);declaredMethod2.setAccessible(true); //私有直接赋值报错,需要开启权限。java.lang.IllegalAccessExceptionString declaredMethod2return = (String) declaredMethod2.invoke(utilObject, "私有方法赋值");System.out.println("declaredMethod2return:"+declaredMethod2return);System.out.println("3、Method的一些常用方法");//Method的一些常用方法System.out.println(declaredMethod2.getParameterCount()); //参数个数System.out.println(Arrays.toString(declaredMethod2.getParameterTypes())); //参数类型System.out.println("4、获取全部的方法");for (Method declaredMethod : aClass.getDeclaredMethods()) {System.out.println(declaredMethod);}}
    }
    
  • 输出结果

    1、获取成员方法 Method
    Util公共方法
    Util公共方法:公共方法赋值
    method2return:公共方法赋值
    2、私有成员方法的获取
    Util私有方法
    Util私有方法:私有方法赋值
    declaredMethod2return:私有方法赋值
    3Method的一些常用方法
    1
    [class java.lang.String]
    4、获取全部的方法
    private void com.universe.test1.Util.getPrivateFun()
    private java.lang.String com.universe.test1.Util.getPrivateFun(java.lang.String)
    public void com.universe.test1.Util.getPublicFun()
    public java.lang.String com.universe.test1.Util.getPublicFun(java.lang.String)
    

4、使用Class中的属性

获取成员的有2*2种方法:
获取单个的公共成员,获取全部的公共成员,获取单个的成员(私有也可以),获取全部的成员(私有也可以)
为什么要获得成员呢,当然是为了用

  • 先创建一个类

    public class User {public String name;private int age;@Overridepublic String toString() {return "User{" +"name='" + name + '\'' +", age=" + age +'}';}
    }
    
  • 通过反射获取成员变量

    import java.lang.reflect.Field;
    public class UserTest {public static void main(String[] args) throws Exception {Class<User> aClass = User.class;System.out.println("获取成员Field的部分");//1、获取公共的成员System.out.println("1、获取公共的成员");User userObject = (User) aClass.getConstructor().newInstance(); //先创建一个实例,用于后续赋值Field field1 = aClass.getField("name");field1.set(userObject, "tang"); //成员赋值,使用setSystem.out.println(userObject);//2、获取私有的成员System.out.println("2、获取私有的成员");//Field field2 = aClass.getField("age"); //私有成员通过getField是获取不到的,				 //报错java.lang.NoSuchFieldExceptionField declaredField1 = aClass.getDeclaredField("age");declaredField1.setAccessible(true); //私有成员直接赋值报错。java.lang.IllegalAccessExceptiondeclaredField1.set(userObject, 22);System.out.println(userObject);//3、Field的常用方法System.out.println("3、Field的常用方法");System.out.println(field1.getName()); //获取成员的名字 nameSystem.out.println(field1.getType()); //获取成员的类型 class java.lang.String//4、获取全部的成员System.out.println("4、获取全部的成员");for (Field declaredField : aClass.getDeclaredFields()) {System.out.println("declaredField:"+declaredField);}}
    }
    
  • 输出结果

    获取成员Field的部分
    1、获取公共的成员
    User{name='tang', age=0}
    2、获取私有的成员
    User{name='tang', age=22}
    3Field的常用方法
    name
    class java.lang.String
    4、获取全部的成员
    declaredField:public java.lang.String com.universe.test1.User.name
    declaredField:private int com.universe.test1.User.age
    

5、使用Class中的注解

通过反射获取注解可是十分重要的内容,目前主流的java框架都在使用注解。
反射使用注解主要有几个方面:
1、如果获取注解呢?获取不到怎么使用呢?使用getAnnotations()
2、也可判断是有没有某个注解。使用isAnnotationPresent()
3、获取到的注解中的方法是可以直接使用的哦

  • 使用注解反射

    import java.lang.annotation.Documented;
    import java.lang.annotation.Retention;
    import java.lang.annotation.RetentionPolicy;
    import java.util.Arrays;public class AnnotationTest {public static void main(String[] args) {Class<MyBean> myBeanClass = MyBean.class;System.out.println(Arrays.toString(myBeanClass.getAnnotations())); //获取全部的注解System.out.println(myBeanClass.isAnnotationPresent(Desc.class)); //判断有没有某个注解Desc desc = myBeanClass.getAnnotation(Desc.class); //可以直接获取到对应的注解System.out.println(desc.myDesc()); //注解方法的调用}
    }
    @Documented
    @Retention(RetentionPolicy.RUNTIME) //编译器将Annotation存储于class文件中,这样才能使用反射获取
    @interface Desc {String myDesc() default "This is an annotation!";
    }@Desc(myDesc = "Class MyBean is used!")
    class MyBean {String name;
    }
    
  • 输出结果

    [@com.universe.test1.Desc(myDesc="Class MyBean is used!")]
    true
    Class MyBean is used!
    

6、Class中的常用方法

通过反射可以获取类的所有信息,想要什么就去找吧

Class<Object> aClass = Object.class;
System.out.println(aClass.getPackage()); //package java.lang
System.out.println(aClass.getPackageName()); //java.lang
System.out.println(aClass.getName()); //java.lang.Object
System.out.println(aClass.getSimpleName()); //Object
System.out.println(aClass.getModifiers()); //1
Class<HashMap> hashMapClass = HashMap.class;
System.out.println(aClass.isAssignableFrom(hashMapClass));
System.out.println(hashMapClass.isAssignableFrom(aClass));
Class<? super HashMap> superclass = hashMapClass.getSuperclass();//获取该类继承的类
System.out.println(superclass); //class java.util.AbstractMap
Class<?>[] interfaces = hashMapClass.getInterfaces(); //获取该类实现的接口
System.out.println(interfaces.length); //3
for (Class<?> anInterface : interfaces) {System.out.println(anInterface.toString());
}
//interface java.util.Map
//interface java.lang.Cloneable
//interface java.io.Serializable
  • getModifiers()方法返回int类型值表示该字段的修饰符。当没有类型时,对应的INT类型是0。
修饰符对应的INT类型修饰符对应的INT类型
public1volatile64
private2transient128
protected4native256
static8interface512
final16abstract1024
synchronized32strict2048

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/645080.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

RK3399平台开发系列讲解(USB篇)BusHound 工具使用介绍

🚀返回专栏总目录 文章目录 一、BusHound简介二、BusHound的下载三、BusHound设备窗口四、BUSHound发送命令窗口沉淀、分享、成长,让自己和他人都能有所收获!😄 📢 BusHound软件是由美国perisoft公司研制的一种专用于PC机各种总线数据包监视和控制的开发工具软件,其名…

前端面试——关于this指向问题?

想要知道关于this的指向问题&#xff0c;首先要了解this的绑定规则。那么this到底是什么样的绑定规则呢&#xff1f;一起来研究一下吧&#xff01; 绑定一&#xff1a;默认绑定 绑定二&#xff1a;饮食绑定 绑定三&#xff1a;显示绑定 绑定四&#xff1a;隐式绑定 1. 默认…

【GitHub项目推荐--一款美观的开源社区系统】【转载】

推荐一款开源社区系统&#xff0c;该系统基于主流的 Java Web 技术栈&#xff0c;如果你是一名 Java 新手掌握了基本 JavaEE 框架知识&#xff0c;可以拿本项目作为练手项目。 开源社区系统功能还算完善包含发布帖子、发布评论、私信、系统通知、点赞、关注、搜索、用户设置、…

What is `Filter` does?

过滤器&#xff08;Filter&#xff09;是Java Servlet规范中的一部分&#xff0c;它提供了一种在请求到达目标资源之前或响应发送给客户端之前进行预处理和后处理的能力。 通过编写自定义的过滤器类并将其注册到Web应用程序中&#xff0c;开发者可以实现诸如登录验证、权限控制…

边缘计算及相关产品历史发展

边缘计算及相关产品历史发展 背景边缘计算的历史CDN&#xff08;Content Delivery Network&#xff09;Cloudlet雾计算MEC&#xff08;Multi-Access Edge Computing&#xff0c;MEC&#xff09; 边缘计算的现状云计算厂商硬件厂商软件基金会 背景 最近&#xff0c;公司部分业务…

RT-DETR优化改进:IoU系列篇 | Focaler-IoU​​​​​​​更加聚焦的IoU损失Focaler-IoU |2024年最新发表

🚀🚀🚀本文改进:Focaler-IoU更加聚焦的IoU损失Focaler-IoU,能够在不同的检测任务中聚焦不同的回归样本,使用线性区间映射的方法来重构IoU损失 🚀🚀🚀RT-DETR改进创新专栏:http://t.csdnimg.cn/vuQTz 🚀🚀🚀学姐带你学习YOLOv8,从入门到创新,轻轻松松搞…

Redis中BigKey的分析与优化

Redis中BigKey的分析与优化 Redis以其出色的性能和易用性&#xff0c;在互联网技术栈中占据了重要的地位。 但是&#xff0c;高效的工具使用不当也会成为性能瓶颈。在Redis中&#xff0c;BigKey是常见的性能杀手之一&#xff0c;它们会消耗过多的内存&#xff0c;导致网络拥塞…

【每日一题】最大交换

文章目录 Tag题目来源解题思路方法一&#xff1a;暴力法方法二&#xff1a;贪心 写在最后 Tag 【暴力法】【贪心法】【数组】【2024-01-22】 题目来源 670. 最大交换 解题思路 本题的数据规模比较小&#xff0c;暴力法也可以通过。以下将会介绍暴力法和本题最优法。 方法一…

14027.ptp 控制流

文章目录 1 ptp 控制流1.1 控制流分层 1 ptp 控制流 1.1 控制流分层 大体分为4层&#xff1a;1 ptp4l层&#xff1a; 获取配置文件、创建时钟、poll监控文件描述符。2 clock时钟层&#xff1a;提供提供clock_poll、clock_create、clock_sync 等3 port 端口层&#xff1a;port…

后端MySQL常用命令

不是专业后端的&#xff0c;所有可能有些不太准确&#xff0c;都是自己平时在项目当中总结的&#xff0c;谢谢ฅฅ* 添加/insert 给指定字段添加数据 INSERT INTO 表名 字段名 VALUES 值 INSERT INTO ninth_student (id,name,sex,age,weight,birth) VALUES (0,亚亚,女,18,4…

为什么重写hashcode要一起重写equals方法

为什要重写hashcode&#xff1f; hashcode方法得到一个hash值其实是要起到一个比较作用&#xff0c;比较两个未知的东西是不是同一个东西&#xff0c;因为我们要求hashcode方法产生的hash值对于”同一个东西“得到的hash值是一样的。 那这种特性可以做到去重的效果&#xff0…

HBase学习五:运维排障之复制

官方文档-HBase复制,包含相关命令信息 0 名词解释 在HBase中,HLog(也称为WAL)用于记录所有对HBase表的修改操作,以便在系统故障时可以恢复数据。 Entry的含义 Entry在HLog上下文中通常指的是WAL中的一个记录项。每个Entry包含了一次或多次对HBase表的修改操作的信息,这…

通过 GScan 工具自动排查后门

一、简介 GScan 是一款为安全应急响应提供便利的工具&#xff0c;自动化监测系统中常见位置。 工具运行环境&#xff1a;CentOS (6、7) python (2.x、3.x) 工具检查项目&#xff1a; 1、主机信息获取 2、系统初始化 alias 检查 3、文件类安全扫描 3.1、系统重要文件完整行…

Express.js 中动态路由解码:path-to-regexp介绍

1. path-to-regexp&#xff1a;将路径转化为模式 path-to-regexp 是一个 Node.js 工具&#xff0c;用于将路径字符串转换为正则表达式。它在像 Express.js 这样的网络框架中广泛用于处理动态路由。 主要功能及代码示例&#xff1a; 将路径转换为正则表达式&#xff1a; 它将带…

linux shell脚本 条件语句

test 测试文本的表达式 是否成立 格式&#xff1a; test 条件表达式 格式&#xff1a; [ 条件表达式 ] &#xff08;[] 内要空格 &#xff0c;不然不生效&#xff09; 如何测试&#xff1f; [ 操作符 文件或目录 ] echo $? 返回值是0 正确&#xff0c;返回值非0 …

Unity——FSM有限状态机

有限状态机就是有限个切换状态的条件&#xff0c;要制作有限状态机&#xff0c;有几个必要点&#xff1a;状态抽象类、FSMSystem类、FSMSystem实现类、FSM状态实现类。 每一个控制者都有一个状态机&#xff0c;每一个状态机都有其包含的状态&#xff0c;每一个状态都有能转换的…

运维之道—生产环境安装mysql

目录 1.前言 2.部署安装 2.1 下载mysql5.7版本的yum仓库 2.2 安装yum仓库 2.3 安装mysql-server 2.4 启动mysql-server 3. 生产配置 3.1 登录mysql 3.2 修改root账户密码 3.3 配置mysql

JFinal项目搭建

JFinal项目搭建 JFinal项目搭建 JFinal项目搭建 首先创建maven项目&#xff1a; 删掉报错的jsp页面&#xff1a; 在pom.xml中加入坐标&#xff1a; <dependency> <groupId>com.jfinal</groupId> <artifactId>jfinal-undertow</artifactId>…

零基础学习【Mybatis Plus】这一篇就够了

学习目录 1. 快速入门1-1. 常用注解总结 1-2. 常用配置 2. 核心功能3. 扩展功能4. 插件功能 1. 快速入门 1-1. 常用注解 MybatisPlus中比较常用的几个注解如下&#xff1a; TableName: 用来指定表名Tableld: 用来指定表中的主键字段信息TableField: 用来指定表中的普通字段信…

基于openssl v3搭建ssl安全加固的c++ tcpserver

1 概述 tcp server和tcp client同时使用openssl库&#xff0c;可对通信双方流通的字节序列进行加解密&#xff0c;保障通信的安全。本文以c编写的tcp server和tcp client为例子&#xff0c;openssl的版本为v3。 2 安装openssl v3 2.1 安装 perl-IPC-Cmd openssl项目中的co…