java多重注解_深入理解java 注解(Annotation)重版

本文介绍了Java注解的基础概念,重点讲解了@Target、@Retention、@Documented和@Inherited这四个元注解的作用,以及如何在权限验证框架中运用。通过实例展示了注解的定义、使用和解析过程,适合进一步理解注解在实际项目中的应用。
摘要由CSDN通过智能技术生成

近期项目需要做权限验证,高手们写了一个权限验证的框架,看了一遍代码,还是和高手有差距啊~

权限框架用到了一些注解反射啥的,所以回头看看以前写的文章《深入理解java 注解(Annotation)》,转过来,再做一些补充,做备忘使用。

一、什么是注解?

懒得去打了,搞一份wiki上的解释,自己看吧(以前可能会翻译一下,现在懒了)

77e04e73239f18137e5391befaff7cbf.png

Annotation的使用方式及自定义注解

首先扫下盲,元注解就是Annotation的元注解一共有4个,分别为:@Target、@Retention、@Documented、@Inherited

1、@Target用来表示声明的Annotation修饰的范围,其ElementType的枚举一共有以下几个

514a750a06c746529529d3350202f92b.png

简单地翻译一下吧

ANNOTATION_TYPE 注解类型声明

CONSTRUCTOR 构造方法声明

FIELD 属性声明

LOCAL_VARIABLE 局部变量性声明

METHOD 方法声明

PACKAGE  包声明

PARAMETER 参数声明

TYPE 类、接口(包括注解类型)或枚举型声明

2、@Retention 表明了注解可以保留多长时间,或者说是在哪个阶段,默认的保存留方案是CLASS,其RetentionPolicy的枚举一共有以下几个

7e57f252ea9d8d8c40520a6164658b28.png

简单地翻译一下吧

CLASS 注解被记录在class文件中,但是在运行的时候不会在虚拟机中保留(即编译阶段有效)

RUNTIME 注解被记录在class文件中,在虚拟机运行时会被保留,因此可以被反射机制读取出来(即在运行阶段仍然有效)(一般我们使用的都是这个)

SOURCE 在编译的时候被编译器丢弃(即源码阶段有效),像java中的几个常见的在编写代码阶段用于编译器报错的注解都是使用这个值:@Override,@Deprecated,@SuppressWarnings

3、@Documented 标注了这个描述的annotation是否可以被文档化。(没什么好说的)

4、@Inherited 表明了注解的类型是自动被继承的。如果一个注解使用了@Inherited这个元注解,则它的子类也会自动添加这个注解(即这个注解是可以被继承的)。

5、jdk1.5后反射的实体都实现了AnnotatedElement的接口,使得读取注解更加地简单,为了节省时间,还是截jdk文档的图吧

282243a9907e2dc0ec5b5fa2479d59d5.png

二、注解有什么用

注解的字面上意思就是解释说明吧。

Java中的用途是对类、方法、属性进行添加注释说明,比如,这个方法/类的路由,权限等。

(以上都是自己YY的)

三、注解怎么用

注解的使用一般分类三步:定义注解、使用注解、解析注解。话不多说,上代码。

1、定义注解

@Inherited

@Documented

@Target(ElementType.TYPE)

@Retention(RetentionPolicy.RUNTIME)

public @interface Controller {

String value();

}

@Inherited

@Documented

@Target(ElementType.FIELD)

@Retention(RetentionPolicy.RUNTIME)

public @interface Inject {

String value();

}

@Inherited

@Documented

@Target({ElementType.TYPE, ElementType.METHOD})

@Retention(RetentionPolicy.RUNTIME)

public @interface Permission {

String value() default "root";

}

@Inherited

@Documented

@Target(ElementType.PARAMETER)

@Retention(RetentionPolicy.RUNTIME)

public @interface Parameter {

String value() default "";

}

@Inherited

@Documented

@Target(ElementType.PARAMETER)

@Retention(RetentionPolicy.RUNTIME)

public @interface Required {}

2、使用注解

@Controller("testController")

public class TestController {

@Inject("injectStr")

private String injectStr;

@Permission("testPmission")

public void test(@Parameter("param") @Required String param, @Required String param2) {}

}

3、解析注解

public class Main {

public static void main(String[] args) {

Class clazz = TestController.class;

if (clazz.isAnnotationPresent(Controller.class)) {

Controller controllerAnnotaion = (Controller) clazz.getAnnotation(Controller.class);

System.out.println("class annotations: " + controllerAnnotaion.value());

}

Field[] fields = clazz.getDeclaredFields();

for (Field field : fields) {

if (field.isAnnotationPresent(Inject.class)) {

System.out.println("field annotations: " + field.getAnnotation(Inject.class).value());

}

}

Method[] methods = clazz.getDeclaredMethods();

for (Method method : methods) {

if (method.isAnnotationPresent(Permission.class)) {

System.out.println("method annotations: " + method.getAnnotation(Permission.class).value());

}

Annotation[][] parameterAnnotations = method.getParameterAnnotations();

for (Annotation[] annotations : parameterAnnotations) {

for (Annotation annotation : annotations) {

System.out.println("parameter annotations: " + annotation.toString());

}

}

}

}

}

参考文章:

Oracle java api (这部分自己去选annotation包下的Class)

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值