博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
JavaWeb学习-注解-3-反射注解
阅读量:4301 次
发布时间:2019-05-27

本文共 4388 字,大约阅读时间需要 14 分钟。

这篇来学习反射注解,前面我们知道如果需要使用反射,那么注解的保留策略一定要是RUNTIME类型。本篇来学习下如何通过反射获取作用在不同目标上的注解内容。

 

反射注解需要从作用目标上返回

  • 类上的注解,需要从Class来获取
  • 方法上的注解,需要从Method来获取
  • 构造器上注解,需要从Construcation来获取
  • 成员上注解,需要从Field上获取

根据前面学的,其实还有其他注解的作用目标,这里我们就看这四个来学习反射注解。上面四个类,Class类单独分一类,后面三个分一类。通过JDK查看后面三个类,都在reflect,反射包下,有一个共同父类AccessibleObject。

 

反射注解练习

这里来一个练习,先定义一个注解,然后看看反射注解。

@Retention(RetentionPolicy.RUNTIME)@interface MyAnnotation{	String name();	int age();	String gender();}

获取作用目标为类上注解信息

package annotation;import java.lang.annotation.Retention;import java.lang.annotation.RetentionPolicy;public class Demo1 {}@MyAnnotation(name="A类", age=18, gender="男")class A{	@MyAnnotation(name="fun1方法", age=19, gender="女")	public void fun1() {			}}@Retention(RetentionPolicy.RUNTIME)@interface MyAnnotation{	String name();	int age();	String gender();}

先准备这段代码,我们在A类上和A类的方法中都使用了注解,那么如何获取A类上的注解信息,也就是如何通过代码拿到name="A类", age=18, gender="男" 这个信息。

package annotation;import java.lang.annotation.Retention;import java.lang.annotation.RetentionPolicy;import org.junit.Test;public class Demo1 {		@Test	public void fun1() {		// 1. 得到作用目标		Class c = A.class;		// 2.获取指定类型的注解,当前我们这里类型就一个 MyAnnotation		MyAnnotation myAn = c.getAnnotation(MyAnnotation.class);		System.out.println(myAn.name() + ", " + myAn.age() + ", " + myAn.gender());	}	}@MyAnnotation(name="A类", age=18, gender="男")class A{	@MyAnnotation(name="fun1方法", age=19, gender="女")	public void fun1() {			}}@Retention(RetentionPolicy.RUNTIME)@interface MyAnnotation{	String name();	int age();	String gender();}

运行输出结果是

A, 18,

 

获取作用目标为方法上注解信息

下面代码来获取A类下的方法fun1()上的注解内容。

package annotation;import java.lang.annotation.Retention;import java.lang.annotation.RetentionPolicy;import java.lang.reflect.Method;import org.junit.Test;public class Demo1 {		@Test	public void fun1() throws ReflectiveOperationException, SecurityException {		// 1. 得到作用目标, 这时候是方法		Class c = A.class;		Method method = c.getMethod("fun1");		// 2.获取指定类型的注解,当前我们这里类型就一个 MyAnnotation		MyAnnotation myAn = method.getAnnotation(MyAnnotation.class);		System.out.println(myAn.name() + ", " + myAn.age() + ", " + myAn.gender());	}	}@MyAnnotation(name="A类", age=18, gender="男")class A{	@MyAnnotation(name="fun1方法", age=19, gender="女")	public void fun1() {			}}@Retention(RetentionPolicy.RUNTIME)@interface MyAnnotation{	String name();	int age();	String gender();}

输出内容

fun1方法, 19,

 

 

获取构造器上注解信息

 

有了前面两个获取的基础,获取构造器就简单了,直接来看下面代码。

package annotation;import java.lang.annotation.Retention;import java.lang.annotation.RetentionPolicy;import java.lang.reflect.Constructor;import java.lang.reflect.Method;import org.junit.Test;public class Demo1 {		@Test	public void fun1() throws ReflectiveOperationException, SecurityException {		// 1. 得到作用目标,		Class c = A.class;		Constructor constructor = c.getConstructor(); // 这种我们没写带参数的构造,参数为空		// 2.获取指定类型的注解,当前我们这里类型就一个 MyAnnotation		MyAnnotation myAn = (MyAnnotation) constructor.getAnnotation(MyAnnotation.class);		System.out.println(myAn.name() + ", " + myAn.age() + ", " + myAn.gender());	}	}@MyAnnotation(name="A类", age=18, gender="男")class A{		// 构造器	@MyAnnotation(name="构造器", age=20, gender="不清楚")	public A() {			}		@MyAnnotation(name="fun1方法", age=19, gender="女")	public void fun1() {			}}@Retention(RetentionPolicy.RUNTIME)@interface MyAnnotation{	String name();	int age();	String gender();}

输出结果

构造器, 20, 不清楚

 

从输出结果来看,我们正确地得到了该作用目标的注解内容,下面来直接看字段注解如何获取。

package annotation;import java.lang.annotation.Retention;import java.lang.annotation.RetentionPolicy;import java.lang.reflect.Field;import org.junit.Test;public class Demo1 {		@Test	public void fun1() throws ReflectiveOperationException, SecurityException {		// 1. 得到作用目标,		Class c = A.class;		Field field = c.getField("userName");		// 2.获取指定类型的注解,当前我们这里类型就一个 MyAnnotation		MyAnnotation myAn = field.getAnnotation(MyAnnotation.class);		System.out.println(myAn.name() + ", " + myAn.age() + ", " + myAn.gender());	}	}@MyAnnotation(name="A类", age=18, gender="男")class A{		@MyAnnotation(name="成员变量", age=23, gender="男")	public String userName;		// 构造器	@MyAnnotation(name="构造器", age=20, gender="不清楚")	public A() {			}		@MyAnnotation(name="fun1方法", age=19, gender="女")	public void fun1() {			}}@Retention(RetentionPolicy.RUNTIME)@interface MyAnnotation{	String name();	int age();	String gender();}

输出结果

成员变量, 23,

 

这里提醒一下,为什么要在A类的成员变量写成public,如果你写成了private,那么就变成不可访问。打开Class的JDK文档,找到getField()方法,明确说了“返回一个 Field 对象,它反映此 Class 对象所表示的类或接口的指定公共成员字段”。

 

转载地址:http://gmxws.baihongyu.com/

你可能感兴趣的文章
vivado模块封装ip/edf
查看>>
sdc时序约束
查看>>
Xilinx Jtag Access/svf文件/BSCANE2
查看>>
NoC片上网络
查看>>
开源SoC整理
查看>>
【2020-3-21】Mac安装Homebrew慢,解决办法
查看>>
influxdb 命令行输出时间为 yyyy-MM-dd HH:mm:ss(年月日时分秒)的方法
查看>>
已知子网掩码,确定ip地址范围
查看>>
判断时间或者数字是否连续
查看>>
docker-daemon.json各配置详解
查看>>
Mac 下docker路径 /var/lib/docker不存在问题
查看>>
Docker(一)使用阿里云容器镜像服务
查看>>
Docker(二) 基础命令
查看>>
Docker(三) 构建镜像
查看>>
Spring 全家桶注解一览
查看>>
JDK1.8-Stream API使用
查看>>
cant connect to local MySQL server through socket /tmp/mysql.sock (2)
查看>>
vue中的状态管理 vuex store
查看>>
Maven之阿里云镜像仓库配置
查看>>
Maven:mirror和repository 区别
查看>>