Java如何快速獲取類附帶的註解

mpsky發表於2021-09-09

作者:  
轉載標誌 【2018-01-04】

更新日誌

日期 更新內容 備註
2018-01-04 建立分析文件 java技術乾貨分享

Java技術乾貨分享

如何快速獲取或者判斷一個類是否有某個註解呢?可以使用物件的Class資訊來獲取,下面是一個例子:

圖片描述

public class AnnotationDemo {    public static boolean hasAnnotation(AnnotatedElement element,
                                        Class extends Annotation> annotationType) {        if (element.isAnnotationPresent(annotationType)) {            return true;
        }        return false;
    }    public static void main(String[] args) {
        Annotations annotations = new Annotations();
        Class> cls = annotations.getClass();        if (hasAnnotation(cls, AnnotationTestA.class)) {
            System.out.println("Annotation Test A");
        }        if (hasAnnotation(cls, AnnotationTestB.class)) {
            System.out.println("Annotation Test B");
        }        if (hasAnnotation(cls, AnnotationTestC.class)) {
            System.out.println("Annotation Test C");
        }
    }

}@Target({ElementType.TYPE})@Retention(RetentionPolicy.RUNTIME)@Documented@interface AnnotationTestA {}@Target({ElementType.TYPE})@Retention(RetentionPolicy.RUNTIME)@Documented@interface AnnotationTestB {}@Target({ElementType.TYPE})@Retention(RetentionPolicy.RUNTIME)@Documented@interface AnnotationTestC {}@AnnotationTestA@AnnotationTestB@AnnotationTestCclass Annotations {}

在上面的例子中,hasAnnotation方法的作用就是判斷是否一個物件所屬的類包含某個註解,可以分析一下具體的實現,首先,第一個引數型別為AnnotatedElement,代表具體需要判斷的物件Class資訊,需要注意的是,Class類實現了AnnotatedElement介面,所以傳遞一個Class物件給這個方法的第一個引數是合法的;第二個引數是註解類的Class資訊,是需要檢測的目標註解。可以看到,在程式碼中使用了AnnotatedElement的isAnnotationPresent方法來進行判斷是否具有某個註解的功能,可以跟進去看一下具體的實現原理。

圖片描述

    default boolean isAnnotationPresent(Class extends Annotation> annotationClass) {        return getAnnotation(annotationClass) != null;
    }    public 

可以看一下annotationData方法的具體實現,參考下面的圖片:

圖片描述

其中首先會判斷是否具有需要的資料,以及是否符合要求,如果資料不存在或者過期了,那麼就需要重新獲取,重新獲取資料的關鍵方法是createAnnotationData,該方法的實現可以參考下面的程式碼:圖片描述

annotationData方法獲取到的是一個AnnotationData物件,可以看一下AnnotationData類的定義:

    // annotation data that might get invalidated when JVM TI RedefineClasses() is called
    private static class AnnotationData {        final Map, Annotation> annotations;        final Map, Annotation> declaredAnnotations;        // Value of classRedefinedCount when we created this AnnotationData instance
        final int redefinedCount;

        AnnotationData(Map, Annotation> annotations,
                       Map, Annotation> declaredAnnotations,                       int redefinedCount) {            this.annotations = annotations;            this.declaredAnnotations = declaredAnnotations;            this.redefinedCount = redefinedCount;
        }
    }

在getAnnotation方法中,該方法獲取了AnnotationData欄位的annotations欄位來判斷是否包含目標註解,更加深入的細節可以自行參考Class類的具體實現。本文是一個極短的java技術分享,提供一種獲取一個物件的註解資訊的思路,其實還有很多型別資訊都是可以透過Class來獲取到的,這方面的內容可以挖掘很多,日後會多往這方面做文章。




來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/1806/viewspace-2809634/,如需轉載,請註明出處,否則將追究法律責任。

相關文章