复合注解的解析
/**
* 复合注解, 注解上面的注解,并且演示怎么进行解析。
*/
public class AnnoTwo {
/**
* 基本的注解
*/
@Target({ElementType.TYPE,ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@interface Base{
public String value() default "";
}
/**复合注解,被基本的注解。**/
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Base("haha")
@interface Two{
}
/**复合注解的具体使用*/
@Two
private String getAll(){
return "ok";
}
/**
* 复合注解的解析
*/
@Test
public void test1() throws NoSuchMethodException, SecurityException{
Class<AnnoTwo> x = AnnoTwo.class;
Method methd = x.getDeclaredMethod("getAll", new Class[]{});
Annotation[] anns = methd.getDeclaredAnnotations(); /**声明的注解*/
Annotation a = null;
for (Annotation ann : anns) {
if (ann.annotationType() == Base.class) {
a = ann;
break;
}
}
if(a==null){
for (Annotation ann : anns) { /**演示只有2层的,多层需要递归处理*/
if (ann.annotationType()!= null && !ann.annotationType().getName().startsWith("java.lang.annotation")) {
Class<? extends Annotation> annParent = ann.annotationType();
Annotation[] anns2 = annParent.getDeclaredAnnotations();
for (Annotation ann2 : anns2) {
if (ann2.annotationType() == Base.class) {
a = ann2;
break;
}
}
}
}
}
if(a==null){
System.out.println("没找到注解");
}else{
Base res = (Base)a;
System.out.println(res.value());
}
}
/**
* springUitls的findAnnotation可以解析注解上面的非lang包下的自定义组合注解(即元注解)
*/
@Test
public void test2() throws NoSuchMethodException, SecurityException{
Class<AnnoTwo> x = AnnoTwo.class;
Method methd = x.getDeclaredMethod("getAll", new Class[]{});
Set<Annotation> visited = new HashSet();
Base base1 = findAnnotation((AnnotatedElement)methd,Base.class, new HashSet());
Base base2 = AnnotationUtils.findAnnotation(methd, Base.class); //可以得到注解上面的注解,没有返回null
System.out.println(base1.value());
System.out.println(base2.value());
}
/**
* 演示spring的实现 (省略类查询过程 )
* @param annotatedElement (class method 等等都实现了这个接口,并且Annotation的jvm实现类也实现此接口)
* @param annotationType 需要查询的注解类型
* @param visited 递归性能优化用
*/
private static <A extends Annotation> A findAnnotation(
AnnotatedElement annotatedElement, Class<A> annotationType, Set<Annotation> visited) {
try {
Annotation[] anns = annotatedElement.getDeclaredAnnotations();
for (Annotation ann : anns) {
if (ann.annotationType() == annotationType) {
return (A) ann;
}
}
for (Annotation ann : anns) {
if (ann!=null && ann.annotationType() != null && !ann.annotationType().getName().startsWith("java.lang.annotation") && visited.add(ann)) { // visited性能优化用。
A annotation = findAnnotation((AnnotatedElement) ann.annotationType(), annotationType, visited);
if (annotation != null) {
return annotation;
}
}
}
}
catch (Throwable ex) {
return null;
}
return null;
}
}
以上案例:Base base = AnnotationUtils.findAnnotation(methd, Base.class); 可直接获得注解的注解(复合注解!)。没有返回null
好好学习,天天向上