1. 程式人生 > >深入理解編譯註解(四)常用介面介紹

深入理解編譯註解(四)常用介面介紹

前言

今天猛然想起一個註解在使用上的問題,就一直在網上搜索資料,問題倒是沒解決,但是看到了一篇非常好的部落格,正好是我這裡缺少的,寫的很不錯,所以直接轉載。

在之前的demo中,為了完成編譯註解的功能,我們引入了com.google.auto.service:auto-service:1.0-rc2,這篇部落格就是重點介紹了裡面的api。

正文

Element和TypeMirror

我覺得這兩個是開發註解處理器最重要的兩個概念,理解這兩個的概念和使用是非常有必要的。

這兩個都是介面,先來看一下Element的定義:

    /** 
     * 表示一個程式元素,比如包、類或者方法,有如下幾種子介面: 
     * ExecutableElement:表示某個類或介面的方法、構造方法或初始化程式(靜態或例項),包括註解型別元素 ; 
     * PackageElement:表示一個包程式元素; 
     * TypeElement:表示一個類或介面程式元素; 
     * TypeParameterElement:表示一般類、介面、方法或構造方法元素的形式型別引數; 
     * VariableElement:表示一個欄位、enum 常量、方法或構造方法引數、區域性變數或異常引數 
     */
public interface Element extends AnnotatedConstruct { /** * 返回此元素定義的型別 * 例如,對於一般類元素 C<N extends Number>,返回引數化型別 C<N> */ TypeMirror asType(); /** * 返回此元素的種類:包、類、介面、方法、欄位...,如下列舉值 * PACKAGE, ENUM, CLASS, ANNOTATION_TYPE, INTERFACE, ENUM_CONSTANT, FIELD, PARAMETER, LOCAL_VARIABLE, EXCEPTION_PARAMETER, * METHOD, CONSTRUCTOR, STATIC_INIT, INSTANCE_INIT, TYPE_PARAMETER, OTHER, RESOURCE_VARIABLE; */
ElementKind getKind(); /** * 返回此元素的修飾符,如下列舉值 * PUBLIC, PROTECTED, PRIVATE, ABSTRACT, DEFAULT, STATIC, FINAL, * TRANSIENT, VOLATILE, SYNCHRONIZED, NATIVE, STRICTFP; */ Set<Modifier> getModifiers(); /** * 返回此元素的簡單名稱,例如 * 型別元素 java.util.Set<E> 的簡單名稱是 "Set"; * 如果此元素表示一個未指定的包,則返回一個空名稱; * 如果它表示一個構造方法,則返回名稱 "<init>"; * 如果它表示一個靜態初始化程式,則返回名稱 "<clinit>"; * 如果它表示一個匿名類或者例項初始化程式,則返回一個空名稱 */
Name getSimpleName(); /** * 返回封裝此元素的最裡層元素。 * 如果此元素的宣告在詞法上直接封裝在另一個元素的宣告中,則返回那個封裝元素; * 如果此元素是頂層型別,則返回它的包; * 如果此元素是一個包,則返回 null; * 如果此元素是一個泛型引數,則返回 null. */ Element getEnclosingElement(); /** * 返回此元素直接封裝的子元素 */ List<? extends Element> getEnclosedElements(); /** * 返回直接存在於此元素上的註解 * 要獲得繼承的註解,可使用 getAllAnnotationMirrors */ @Override List<? extends AnnotationMirror> getAnnotationMirrors(); /** * 返回此元素針對指定型別的註解(如果存在這樣的註解),否則返回 null。註解可以是繼承的,也可以是直接存在於此元素上的 */ @Override <A extends Annotation> A getAnnotation(Class<A> annotationType); }

Element 代表程式的元素,在註解處理過程中,編譯器會掃描所有的Java原始檔,並將原始碼中的每一個部分都看作特定型別的 Element。它可以代表包、類、介面、方法、欄位等多種元素種類,具體看getKind()方法中所指代的種類,每個Element 代表一個靜態的、語言級別的構件。

Element 有五個直接子介面,它們分別代表一種特定型別的元素,如下:

PackageElement 表示一個包程式元素
TypeElement 表示一個類或介面程式元素
VariableElement 表示一個欄位、enum 常量、方法或構造方法引數、區域性變數或異常引數
ExecutableElement 表示某個類或介面的方法、構造方法或初始化程式(靜態或例項),包括註解型別元素
TypeParameterElement 表示一般類、介面、方法或構造方法元素的泛型引數

在開發中Element可根據實際情況強轉為以上5種中的一種,它們都帶有各自獨有的方法,來看個簡單的例子:

package com.example;        // PackageElement  

    import java.util.List;  

    public class Sample         // TypeElement  
            <T extends List> {  // TypeParameterElement  

        private int num;        // VariableElement  
        String name;            // VariableElement  

        public Sample() {}      // ExecuteableElement  

        public void setName(    // ExecuteableElement  
                String name     // VariableElement  
                ) {}  
    }  

原始碼中的每個部分都作為一個Element,而TypeElement對應著一種更具體的型別元素。根據上面的表格可以知道,一種特定的元素一般不止指代一種元素種類(ElementKind),比如TypeElement可以指代類或介面,要知道一個元素的準確的種類需要呼叫getKind()方法,該方法返回一個ElementKind列舉值來表示具體種類,如下:

    public enum ElementKind {  

        /** A package. */  
        PACKAGE,  
        /** An enum type. */  
        ENUM,  
        /** A class not described by a more specific kind (like {@code ENUM}). */  
        CLASS,  
        /** An annotation type. */  
        ANNOTATION_TYPE,  
        /** An interface not described by a more specific kind */  
        INTERFACE,  

        // Variables  
        /** An enum constant. */  
        ENUM_CONSTANT,  
        /** A field not described by a more specific kind */  
        FIELD,  
        /** A parameter of a method or constructor. */  
        PARAMETER,  
        /** A local variable. */  
        LOCAL_VARIABLE,  
        /** A parameter of an exception handler. */  
        EXCEPTION_PARAMETER,  

        // Executables  
        /** A method. */  
        METHOD,  
        /** A constructor. */  
        CONSTRUCTOR,  
        /** A static initializer. */  
        STATIC_INIT,  
        /** An instance initializer. */  
        INSTANCE_INIT,  
        /** A type parameter. */  
        TYPE_PARAMETER,  

        /** An implementation-reserved element. This is not the element you are looking for. */  
        OTHER,  
        /** 
         * A resource variable. 
         * @since 1.7 
         */  
        RESOURCE_VARIABLE;  
    }  

上面管ElementKind稱作元素的種類,因為它和元素的型別TypeMirror很容易混掉。TypeMirror表示的是 Java 程式語言中的型別,比如上面例子中的欄位String name,它的元素種類為FIELD,而它的元素型別為DECLARED表示一個類型別,這裡對應Java 程式語言中的型別為java.lang.String。Element代表的是原始碼上的元素,TypeMirror代表的是Element對應Java 程式語言中的型別。

    /** 
     * 表示 Java 程式語言中的型別 
     */  
    public interface TypeMirror {  
        /** 
         * 返回此型別的種類,一個 TypeKind 列舉值: 
         */  
        TypeKind getKind();  
    }  

TypeMirror和Element一樣有一個getKind()方法來獲取具體的型別,方法返回一個列舉值,如下:

    public enum TypeKind {  
        /** The primitive type {@code boolean}. */  
        BOOLEAN,  
        /** The primitive type {@code byte}. */  
        BYTE,  
        /** The primitive type {@code short}. */  
        SHORT,  
        /** The primitive type {@code int}. */  
        INT,  
        /** The primitive type {@code long}. */  
        LONG,  
        /** The primitive type {@code char}. */  
        CHAR,  
        /** The primitive type {@code float}. */  
        FLOAT,  
        /** The primitive type {@code double}. */  
        DOUBLE,  
        /** The pseudo-type corresponding to the keyword {@code void}. */  
        VOID,  
        /** A pseudo-type used where no actual type is appropriate. */  
        NONE,  
        /** The null type. */  
        NULL,  
        /** An array type. */  
        ARRAY,  
        /** A class or interface type. */  
        DECLARED,  
        /** A class or interface type that could not be resolved. */  
        ERROR,  
        /** A type variable. */  
        TYPEVAR,  
        /** A wildcard type argument. */  
        WILDCARD,  
        /** A pseudo-type corresponding to a package element. */  
        PACKAGE,  
        /** A method, constructor, or initializer. */  
        EXECUTABLE,  
        /** An implementation-reserved type. This is not the type you are looking for. */  
        OTHER,  
        /** A union type. */  
        UNION,  
        /** An intersection type. */  
        INTERSECTION;  
    }  

可以看到和ElementKind所描述的是不同的方面。不知道這樣說明的清不清楚,其實這種概念上的東西自己用幾次會有更好理解,這東西就說到這。

Element的直接子介面

這裡列一下5個Element子介面常用方法,大部分描述是從JDK PAI手冊中擷取。這東西你也沒必要一次看完,大概瞭解一下,等到需要用的時候能夠知道有這麼個東西就行了。

    /** 
     * 表示一個類或介面程式元素 
     */  
    public interface TypeElement {  

        /** 
         * 返回此型別元素的嵌套種類 
         * 某一型別元素的嵌套種類 (nesting kind)。型別元素的種類有四種:top-level(頂層)、member(成員)、local(區域性)和 anonymous(匿名) 
         */  
        NestingKind getNestingKind();  

        /** 
         * 返回此型別元素的完全限定名稱。更準確地說,返回規範 名稱。對於沒有規範名稱的區域性類和匿名類,返回一個空名稱. 
         * 一般型別的名稱不包括對其形式型別引數的任何引用。例如,介面 java.util.Set<E> 的完全限定名稱是 "java.util.Set" 
         */  
        Name getQualifiedName();  

        /** 
         * 返回此型別元素的直接超類。如果此型別元素表示一個介面或者類 java.lang.Object,則返回一個種類為 NONE 的 NoType 
         */  
        TypeMirror getSuperclass();  

        /** 
         * 返回直接由此類實現或直接由此介面擴充套件的介面型別 
         */  
        List<? extends TypeMirror> getInterfaces();  

        /** 
         * 按照宣告順序返回此型別元素的形式型別引數 
         */  
        List<? extends TypeParameterElement> getTypeParameters();  
    } 

PackageElement

    /** 
     * 表示一個包程式元素. 
     */  
    public interface PackageElement {  

        /** 
         * 返回此包的完全限定名稱。該名稱也是包的規範名稱 
         */  
        Name getQualifiedName();  

        /** 
         * 如果此包是一個未命名的包,則返回 true,否則返回 false 
         */  
        boolean isUnnamed();  
    }  

ExecutableElement

    /** 
     * 表示某個類或介面的方法、構造方法或初始化程式(靜態或例項),包括註解型別元素 
     */  
    public interface ExecutableElement {  

        /** 
         * 獲取按照宣告順序返回形式型別引數元素 
         */  
        List<? extends TypeParameterElement> getTypeParameters();  

        /** 
         * 獲取返回的型別元素 
         */  
        TypeMirror getReturnType();  

        /** 
         * 獲取形參元素 
         */  
        List<? extends VariableElement> getParameters();  

        /** 
         * 如果此方法或構造方法接受可變數量的引數,則返回 true,否則返回 false 
         */  
        boolean isVarArgs();  

        /** 
         * 按宣告順序返回此方法或構造方法的 throws 子句中所列出的異常和其他 throwable 
         */  
        List<? extends TypeMirror> getThrownTypes();  

        /** 
         * 如果此 executable 是一個註解型別元素,則返回預設值。如果此方法不是註解型別元素,或者它是一個沒有預設值的註解型別元素,則返回 null 
         */  
        AnnotationValue getDefaultValue();  
    }  

VariableElement

    /** 
     * 表示一個欄位、enum 常量、方法或構造方法引數、區域性變數或異常引數 
     */  
    public interface VariableElement {  

        /** 
         * 如果此變數是一個被初始化為編譯時常量的 static final 欄位,則返回此變數的值。否則返回 null。 
         * 該值為基本型別或 String,如果該值為基本型別,則它被包裝在適當的包裝類中(比如 Integer)。 
         * 注意,並非所有的 static final 欄位都將具有常量值。特別是,enum 常量不 被認為是編譯時常量。要獲得一個常量值,欄位的型別必須是基本型別或 String 
         */  
        Object getConstantValue();  
    }  

TypeParameterElement

    /** 
     * 表示一般類、介面、方法或構造方法元素的泛型引數. 
     */  
    public interface TypeParameterElement {  

        /** 
         * 返回由此型別引數引數化的一般類、介面、方法或構造方法 
         */  
        Element getGenericElement();  

        /** 
         * 返回此型別引數的邊界。它們是用來宣告此型別引數的 extends 子句所指定的型別。 
         * 如果沒有使用顯式的 extends 子句,則認為 java.lang.Object 是唯一的邊界 
         */  
        List<? extends TypeMirror> getBounds();  
    }  

註解處理器的輔助介面

在自定義註解處理器的初始化介面,可以獲取到以下4個輔助介面:

    public class MyProcessor extends AbstractProcessor {  

        private Types typeUtils;  
        private Elements elementUtils;  
        private Filer filer;  
        private Messager messager;  

        @Override  
        public synchronized void init(ProcessingEnvironment processingEnv) {  
            super.init(processingEnv);  
            typeUtils = processingEnv.getTypeUtils();  
            elementUtils = processingEnv.getElementUtils();  
            filer = processingEnv.getFiler();  
            messager = processingEnv.getMessager();  
        }  
    }  

其中Filer之前有用過,一般我們會用它配合JavaPoet來生成我們需要的.java檔案,這裡就不再提它的用法。

Messager

Messager提供給註解處理器一個報告錯誤、警告以及提示資訊的途徑。它不是註解處理器開發者的日誌工具,而是用來寫一些資訊給使用此註解器的第三方開發者的。在官方文件中描述了訊息的不同級別中非常重要的是Kind.ERROR,因為這種型別的資訊用來表示我們的註解處理器處理失敗了。很有可能是第三方開發者錯誤的使用了註解。這個概念和傳統的Java應用有點不一樣,在傳統Java應用中我們可能就丟擲一個異常Exception。如果你在process()中丟擲一個異常,那麼執行註解處理器的JVM將會崩潰(就像其他Java應用一樣),使用我們註解處理器第三方開發者將會從javac中得到非常難懂的出錯資訊,因為它包含註解處理器的堆疊跟蹤(Stacktace)資訊。因此,註解處理器就有一個Messager類,它能夠列印非常優美的錯誤資訊。除此之外,你還可以連線到出錯的元素。在像現在的IDE(整合開發環境)中,第三方開發者可以直接點選錯誤資訊,IDE將會直接跳轉到第三方開發者專案的出錯的原始檔的相應的行。

看下介面程式碼:

    public interface Messager {  

        void printMessage(Diagnostic.Kind kind, CharSequence msg);  

        void printMessage(Diagnostic.Kind kind, CharSequence msg, Element e);  

        void printMessage(Diagnostic.Kind kind, CharSequence msg, Element e, AnnotationMirror a);  

        void printMessage(Diagnostic.Kind kind, CharSequence msg, Element e, AnnotationMirror a, AnnotationValue v);  
    }  

方法都比較好懂,主要需要指定列印的資訊型別和描述字串。

Types
Types是一個用來處理TypeMirror的工具,看下程式碼就好了,提供的方法如下:

    /** 
     * 一個用來處理TypeMirror的工具 
     */  
    public interface Types {  
        /** 
         * 返回對應於型別的元素。該型別可能是 DeclaredType 或 TypeVariable。如果該型別沒有對應元素,則返回 null. 
         */  
        Element asElement(TypeMirror t);  

        /** 
         * 測試兩個 TypeMirror 物件是否表示同一型別. 
         * 警告:如果此方法兩個引數中有一個表示萬用字元,那麼此方法將返回 false 
         */  
        boolean isSameType(TypeMirror t1, TypeMirror t2);  

        /** 
         * 測試一種型別是否是另一個型別的子型別。任何型別都被認為是其本身的子型別. 
         * 
         * @return 當且僅當第一種型別是第二種型別的子型別時返回 true 
         * @throws IllegalArgumentException 如果給定一個 executable 或 package 型別 
         */  
        boolean isSubtype(TypeMirror t1, TypeMirror t2);  

        /** 
         * 測試一種型別是否可以指派給另一種型別. 
         * 
         * @return 當且僅當第一種型別可以指派給第二種型別時返回 true 
         * @throws IllegalArgumentException 如果給定一個 executable 或 package 型別 
         */  
        boolean isAssignable(TypeMirror t1, TypeMirror t2);  

        /** 
         * 測試一個型別引數是否包含 另一個型別引數. 
         * 
         * @return 當且僅當第一種型別包含第二種型別時返回 true 
         * @throws IllegalArgumentException 如果給定一個 executable 或 package 型別 
         */  
        boolean contains(TypeMirror t1, TypeMirror t2);  

        /** 
         * 測試一個方法的簽名是否是另一個方法的子簽名. 
         * 
         * @return 當且僅當第一個簽名是第二個簽名的子簽名時返回 true 
         */  
        boolean isSubsignature(ExecutableType m1, ExecutableType m2);  

        /** 
         * 返回型別的直接超型別。interface 型別將出現在列表的最後(如果有). 
         * 
         * @return 直接超型別;如果沒有,則返回一個空列表 
         * @throws IllegalArgumentException 如果給定一個 executable 或 package 型別 
         */  
        List<? extends TypeMirror> directSupertypes(TypeMirror t);  

        /** 
         * 返回刪除狀態的型別. 
         * 
         * @return 刪除狀態的給定型別 
         * @throws IllegalArgumentException 如果給定一個 package 型別 
         */  
        TypeMirror erasure(TypeMirror t);  

        /** 
         * 返回給定基本型別的裝箱 (boxed) 值型別的類。即應用 boxing 轉換. 
         * 
         * @param p  要轉換的基本型別 
         * @return 型別 p 的裝箱值型別的類 
         */  
        TypeElement boxedClass(PrimitiveType p);  

        /** 
         * 返回給定型別的拆箱 (unboxed) 值型別(基本型別)。即應用 unboxing 轉換. 
         * 
         * @param t  要拆箱的型別 
         * @return 型別 t 的拆箱值型別 
         * @throws IllegalArgumentException 如果給定型別無法進行 unboxing 轉換 
         */  
        PrimitiveType unboxedType(TypeMirror t);  

        /** 
         * 對型別應用 capture 轉換. 
         * 
         * @return 應用 capture 轉換的結果 
         * @throws IllegalArgumentException 如果給定 executable 或 package 型別 
         */  
        TypeMirror capture(TypeMirror t);  

        /** 
         * 返回基本型別. 
         * 
         * @param kind  要返回的基本型別的種類 
         * @return 一個基本型別 
         * @throws IllegalArgumentException 如果 kind 不是基本種類 
         */  
        PrimitiveType getPrimitiveType(TypeKind kind);  

        /** 
         * 返回 null 型別。該型別是 null 的型別. 
         */  
        NullType getNullType();  

        /** 
         * 返回在實際型別不適用的地方所使用的偽型別。 
         * 要返回的型別的種類可以是 VOID 或 NONE。對於包,可以使用 Elements.getPackageElement(CharSequence).asType() 替代. 
         * 
         * @param kind  要返回的型別的種類 
         * @return 種類 VOID 或 NONE 的偽型別 
         * @throws IllegalArgumentException 如果 kind 無效 
         */  
        NoType getNoType(TypeKind kind);  

        /** 
         * 返回具有指定元件型別的陣列型別. 
         * 
         * @throws IllegalArgumentException 如果元件型別對於陣列無效 
         */  
        ArrayType getArrayType(TypeMirror componentType);  

        /** 
         * 返回新的萬用字元型別引數。可以指定萬用字元邊界中的一個,也可以都不指定,但不能都指定. 
         * 
         * @param extendsBound  擴充套件(上)邊界;如果沒有,則該引數為 null 
         * @param superBound    超(下)邊界;如果沒有,則該引數為 null 
         * @return 新的萬用字元 
         * @throws IllegalArgumentException 如果邊界無效 
         */  
        WildcardType getWildcardType(TypeMirror extendsBound,  
                                     TypeMirror superBound);  

        /** 
         * 返回對應於型別元素和實際型別引數的型別。例如,如果給定 Set 的型別元素和 String 的型別映象,那麼可以使用此方法獲取引數化型別 Set<String>. 
         * 
         * 型別引數的數量必須等於型別元素的形式型別引數的數量,或者等於 0。如果等於 0,並且型別元素是泛型,則返回該型別元素的原始型別. 
         * 
         * 如果返回一個引數化型別,則其型別元素不得包含在一般外部類中。 
         * 例如,首先使用此方法獲取型別 Outer<String>,然後呼叫 getDeclaredType(DeclaredType, TypeElement, TypeMirror...), 
         * 可以構造引數化型別 Outer<String>.Inner<Number>. 
         * 
         * @param typeElem  型別元素 
         * @param typeArgs  實際型別引數 
         * @return 對應於型別元素和實際型別引數的型別 
         * @throws IllegalArgumentException 如果給定的型別引數太多或太少,或者提供不合適的型別引數或型別元素 
         */  
        DeclaredType getDeclaredType(TypeElement typeElem, TypeMirror... typeArgs);  

        /** 
         * 根據給定的包含型別,返回對應於型別元素和實際型別引數的型別(它是給定包含型別的成員).例子如上 
         * 如果包含型別是一個引數化型別,則型別引數的數量必須等於 typeElem 的形式型別引數的數量。 
         * 如果包含型別不是引數化的,或者為 null,則此方法等效於 getDeclaredType(typeElem, typeArgs). 
         * 
         * @param containing  包含型別;如果沒有,則該引數為 null 
         * @param typeElem  型別元素 
         * @param typeArgs  實際型別引數 
         * @return 對應於型別元素和實際型別引數的型別,該型別包含在給定型別中 
         * @throws IllegalArgumentException 如果給定的型別引數太多或太少,或者提供了不合適的型別引數、型別元素或包含型別 
         */  
        DeclaredType getDeclaredType(DeclaredType containing,  
                                     TypeElement typeElem, TypeMirror... typeArgs);  

        /** 
         * 當元素被視為給定型別的成員或者直接由給定型別包含時,返回該元素的型別。 
         * 例如,被視為引數化型別 Set<String> 的成員時,Set.add 方法是引數型別為 String 的 ExecutableType. 
         * 
         * @param containing  包含型別 
         * @param element     元素 
         * @return 從包含型別來看的元素的型別 
         * @throws IllegalArgumentException 如果元素對於給定型別無效 
         */  
        TypeMirror asMemberOf(DeclaredType containing, Element element);  
    }  

Elements
Elements是一個用來處理Element的工具,提供的方法如下:

    /** 
     * 一個用來處理Element的工具 
     */  
    public interface Elements {  

        /** 
         * 返回已給出其完全限定名稱的包. 
         * 
         * @param name  完全限定的包名稱;對於未命名的包,該引數為 "" 
         * @return 指定的包;如果沒有找到這樣的包,則返回 null 
         */  
        PackageElement getPackageElement(CharSequence name);  

        /** 
         * 返回已給出其規範名稱的型別元素. 
         * 
         * @param name  規範名稱 
         * @return 指定的型別元素;如果沒有找到這樣的元素,則返回 null 
         */  
        TypeElement getTypeElement(CharSequence name);  

        /** 
         * 返回註釋元素的值,包括預設值. 
         * 此值是以對映的形式返回的,該對映將元素與其相應的值關聯。只包括那些註釋中明確存在其值的元素,不包括那些隱式假定其預設值的元素。 
         * 對映的順序與值出現在註釋源中的順序匹配 
         * 
         * @see AnnotationMirror#getElementValues() 
         * @param a  要檢查的註釋 
         * @return 註釋元素的值,包括預設值 
         */  
        Map<? extends ExecutableElement, ? extends AnnotationValue>  
        getElementValuesWithDefaults(AnnotationMirror a);  

        /** 
         * 返回元素的文件("Javadoc")註釋文字 
         * 
         * @param e  將被檢查的元素 
         * @return 元素的文件註釋;如果沒有,則返回 null 
         */  
        String getDocComment(Element e);  

        /** 
         * 如果元素已過時,則返回 true,否則返回 false. 
         * 
         * @param e  將被檢查的元素 
         * @return 如果元素已過時,則返回 true,否則返回 false 
         */  
        boolean isDeprecated(Element e);  

        /** 
         * 返回型別元素的二進位制名稱. 
         * 
         * @param type  將被檢查的型別元素 
         * @return 二進位制名稱 
         */  
        Name getBinaryName(TypeElement type);  

        /** 
         * 返回元素的包。包的包是它本身. 
         * 
         * @param type 將被檢查的元素 
         * @return 元素的包 
         */  
        PackageElement getPackageOf(Element type);  

        /** 
         * 返回型別元素的所有成員,不管是繼承的還是直接宣告的。對於一個類,結果還包括其構造方法,但不包括區域性類或匿名類. 
         * 
         * 注意,使用 ElementFilter 中的方法可以隔離某個種類的元素. 
         * 
         * @param type  將被檢查的型別 
         * @return 型別的所有成員 
         */  
        List<? extends Element> getAllMembers(TypeElement type);  

        /** 
         * 返回元素的所有註釋,不管是繼承的還是直接存在的. 
         * 
         * @param e  將被檢查的元素 
         * @return 元素的所有註釋 
         */  
        List<? extends AnnotationMirror> getAllAnnotationMirrors(Element e);  

        /** 
         * 測試一個型別、方法或欄位是否隱藏了另一個型別、方法或欄位. 
         * 
         * @param hider   第一個元素 
         * @param hidden  第二個元素 
         * @return 當且僅當第一個元素隱藏了第二個元素時返回 true 
         */  
        boolean hides(Element hider, Element hidden);  

        /** 
         * 測試一個方法(作為給定型別的成員)是否重寫了另一個方法。當非抽象方法重寫抽象方法時,還可以說成是前者實現 了後者. 
         * 
         * @param overrider  第一個方法,可能是 overrider 
         * @param overridden  第二個方法,可能被重寫 
         * @param type   第一個方法是其成員的型別 
         * @return 當且僅當第一個方法重寫第二個方法時返回 true 
         */  
        boolean overrides(ExecutableElement overrider, ExecutableElement overridden,  
                          TypeElement type);  

        /** 
         * 返回表示基本值或字串的常量表達式 文字。返回文字的形式是一種適合於表示原始碼中的值的形式. 
         * 
         * @param value  基本值或字串 
         * @return 常量表達式的文字 
         * @throws IllegalArgumentException 如果引數不是基本值或字串 
         * 
         * @see VariableElement#getConstantValue() 
         */  
        String getConstantExpression(Object value);  

        /** 
         * 按指定順序將元素的表示形式列印到給定 writer。此方法的主要用途是診斷。輸出的具體格式沒有 指定並且是可以更改的. 
         * 
         * @param w 輸出列印到的 writer 
         * @param elements 要列印的元素 
         */  
        void printElements(java.io.Writer w, Element... elements);  

        /** 
         * 返回與引數具有相同字元序列的名稱. 
         * 
         * @param cs 將以名稱形式返回的字元序列 
         * @return 返回與引數具有相同字元序列的名稱 
         */  
        Name getName(CharSequence cs);  

        /** 
         * 如果型別是一個泛型介面則返回 true,否則返回 false 
         * 
         * @param type 將被檢查的型別 
         * @return 如果型別是一個泛型介面則返回 true,否則返回 false 
         * @since 1.8 
         */  
        boolean isFunctionalInterface(TypeElement type);  
    }  

總結

篇幅稍微有點長,大家可以耐心的看,看完之後,對之前的demo的理解肯定又上升了一個水平。可能在複製的過程中,排版出現了一些變化,如果覺得不太美觀的話,可以去檢視原文。