Loading

Java元注解

工作过程中遇到以下需求:校验某些类的某些字符串属性的长度。
由于不想对所有的类和属性进行枚举检查,因此,我想通过在类上添加自定义注解的方式过滤出这些类以及属性。故学习一下Java的元注解。

Java元注解

这里需要说一下Java的内置注解,因为Java里有几个针对注解的注解,即元注解。

@Retention

Indicates how long annotations with the annotated type are to be retained. If no Retention annotation is present on an annotation type declaration, the retention policy defaults to RetentionPolicy.CLASS.
A Retention meta-annotation has effect only if the meta-annotated type is used directly for annotation. It has no effect if the meta-annotated type is used as a member type in another annotation type.

这是Java关于@Retention的注解说明,此注解用于指示被@Retention注解的注解保留多久,默认是RententionPolicy.CLASS。具体可选值如下:

Annotations are to be discarded by the compiler.

SOURCE:会被编译器忽略

Annotations are to be recorded in the class file by the compiler but need not be retained by the VM at run time. This is the default behavior.

CLASS:编译器会保留但是JVM会忽略

Annotations are to be recorded in the class file by the compiler and retained by the VM at run time, so they may be read reflectively.

RUNTIME:运行时依旧保留,所以可以通过反射获得此注解

@Documented

Indicates that annotations with a type are to be documented by javadoc and similar tools by default. This type should be used to annotate the declarations of types whose annotations affect the use of annotated elements by their clients. If a type declaration is annotated with Documented, its annotations become part of the public API of the annotated elements.

有此注解的注解将默认被javadoc或类似工具记录。

@Target

此注解用于指示当前被注解的注解可以使用的范围,例如:

@Target(ElementType.TYPE)
public @interface AAA{
  // TODO
}

以上代码中,AAA注解可用于其他类上。
其可选参数为java.lang.annotation.ElementType枚举类,具体说明不列出来了,大概说明下常用的几个:

  • TYPE:注解可用于类、接口等
  • FIELD:注解可用于字段和枚举常量
  • METHOD:注解可用于方法
  • PARAMETER:注解可用于方法参数
  • CONSTRUCTOR:注解可用于构造器
  • LOCAL_VARIABLE:注解可用于局部变量
  • ANNOTATION_TYPE:注解可用于其他注解
  • TYPE_PARAMETER:注解可用于泛型参数

@Inherited

Indicates that an annotation type is automatically inherited. If an Inherited meta-annotation is present on an annotation type declaration, and the user queries the annotation type on a class declaration, and the class declaration has no annotation for this type, then the class's superclass will automatically be queried for the annotation type. This process will be repeated until an annotation for this type is found, or the top of the class hierarchy (Object) is reached. If no superclass has an annotation for this type, then the query will indicate that the class in question has no such annotation.

举例说明下,一个注解@A,它的注解上有@Inherited时,那么当类ClassA被@A注解时,ClassA的子类ClassB也将继承@A,但仅限于超类子类中,接口和类实现接口里@Inherited不起作用。

@Repeatable

被此注解修饰的注解可重复使用,直接举例:

@Repeatable(AAAs.class)
public @interface AAA{
  String value();
}

public @interface AAAs{
  AAA[] value();
}

@AAA("bbb")
@AAA("ccc")
public class BBB{
  // TODO
}

此注解在1.8时加入,实际为语法糖。

posted @ 2023-09-04 11:47  星流残阳  阅读(4)  评论(0编辑  收藏  举报