具有所有我的自定义注释的通用基本类型

时间:2019-09-20 13:33:20

标签: java inheritance reflection annotations java-annotations

因此,我创建了几个自定义注释:

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface Foo {

}

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface Bar {

}

在我的函数中使用了这些注释:

public class Worker {

   @Foo
   public void doTaskOne() {...}

   @Bar
   public void doTaskX() {...}

   ...
}

我想使用Java反射来检查是否在一种方法中声明了某些注释。

for (Method m : methods) {
      if (m.isAnnotationPresent(Foo.class)) {
        ...
      } else if (m.isAnnotationPresent(Bar.class)) {
        ...
      }
}

问题在于,由于在Java中,自定义注释@interface无法扩展。我的意思是这是非法的:

public @interface Bar extends MyBaseAnnotation{
}

那我的所有自定义注释类@interfaceFoo都没有基础Bar。因此,如果我创建了一个新的自定义注释,则需要在上述方法检查代码中添加更多else if条件,这太糟了!反正有摆脱这个问题的方法吗?我要实现的是将我的方法检查代码概括为:

for (Method m : methods) {
     if (m.isAnnotationPresent(MyBaseAnnotation.class)) {
         ...
     }
}

如何实现?

2 个答案:

答案 0 :(得分:0)

您可以使用基本的自定义注释来注释自定义注释,例如composed annotations

代替:

public @interface Bar extends MyBaseAnnotation{
}

使用:

@MyBaseAnnotation
public @interface Bar {
}

答案 1 :(得分:0)

假设

@Parent
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
@interface Foo {}

@Parent
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
@interface Bar {}

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.ANNOTATION_TYPE)
@interface Parent {}

有一种方法

public static boolean isAnnotationPresent(Method method, Class<? extends Annotation> parentAnnotation) throws NoSuchMethodException {
    for (Annotation methodAnnotation : method.getDeclaredAnnotations()) {
        if (methodAnnotation.annotationType().isAnnotationPresent(parentAnnotation)) {
            return true;
        }
    }
    return false;
}

你可以做

isAnnotationPresent(m, Parent.class)

您做对了:Java中的注释类型之间没有继承。不过,您可以制定自己的规则。通过说“如果注释B在其上具有注释A,则B扩展了A”,可以定义使用反射时要遵循的规则。