註釋型別(Annotation Type)

Java SE 5.0+ (API Docs 本身就是一本最棒的參考書!, 下列來源多取自其內容說明.)

(下列內容大多參考由 WisdomFish, Kuo 所反製的 Java SE 6 正體中文文檔.)



軟體套件 java.lang.annotation


為 Java 程式語言註釋設施提供資源庫支持。

介面摘要
Annotation 所有 annotation 型別都必要擴展的公共介面。(正規介面, 不需 'extends', 自動即俱備其身份.)
 

列舉摘要
ElementType 程序元素型別。(做為 @Target 的內容選項.)
RetentionPolicy 註釋保留策略。(做為 @Retention 的內容選項.)
 

異常摘要
AnnotationTypeMismatchException 若某個註釋的型別在對該註釋進行編譯(或序列化)後發生了更改,而程序試圖存取該註釋的元素時,拋出此異常。
IncompleteAnnotationException 若某個註釋在編譯(或序列化)後將某個註釋型別添加到其型別定義中,而程序試圖該註釋型別的元素時,拋出此異常。
 

錯誤摘要
AnnotationFormatError 當註釋解析器試圖從類別檔案讀取註釋並確定註釋出現異常時,拋出該錯誤。
 

註釋型別摘要
Documented 指示某一型別的註釋將通過 javadoc 和類似的預設工具進行文檔化。
Inherited 指示註釋型別被自動繼承。
Retention 指示註釋型別的註釋要保留多久。(內容選項參考至 RetentionPolicy.)
Target 指示註釋型別所適用的程序元素的種類別。(內容選項參考至 ElementType.)



Annotation學習資源選


Java Annotation入門
Java Annotation手冊



使用者特性


  • 可用於大多數的程序定義處
  • 原則上只對 Compiler 或是特定分析 Tool 有作用
  • 使用時可標列 Full-Package 路徑


開發者撰寫規則


  1. 隱性正規繼承自 Interface : java.lang.annotation.Annotation (無法被擴展)
  2. 不得再繼承其它 Annotation or Interface
  3. 可加諸存取權限範圍, 一般均為 public


Package java.lang.*


註釋型別摘要
Deprecated 用 @Deprecated 註釋的程序元素,不鼓勵開發人員使用這樣的元素,通常是因為它很危險或存在更好的選擇。
Override 表示一個方法宣告打算覆寫父級類別中的另一個方法宣告。(堅持使用Override注釋.Effective Java, NO.36:降低錯鋘率)
SuppressWarnings 指示應該在註釋元素(以及包含在該註釋元素中的所有程序元素)中取消顯示指定的編譯器警告。

Marker Annotation Type

  • @Override
  • @Deprecated
    • unckecked, <Generics>

Single-Value Annotation Type

  • @SuppressWarnings



@Documented


java.lang.annotation
註釋型別 Documented


@Documented
@Retention(value=RUNTIME)
@Target(value=ANNOTATION_TYPE)
public @interface Documented

指示某一型別的註釋將通過 javadoc 和類似的預設工具進行文檔化。應使用此型別來註釋這些型別的宣告:其註釋會影響由其客戶端註釋的元素的使用。如果型別宣告是用 Documented 來註釋的,則其註釋將成為註釋元素的公共 API 的一部分。





自定義 Annotation Type




Marker Annotation

modifiers @interface AnnotationName { elements declaration 0..N; }


Single-Value Annotation

  • 值以方法()型參存在
  • type elementName() default value;

public @interface BaGua {

// public abstract String value
String value();
}

操作....
@BaGua("Hello") <---單值注釋可被簡化的方式
@BaGua(value="Hello")


Array, [] => @BaGua(value={"Hello", "Hello2"})  || @@BaGua({"Hello", "Hello2"})



Multi-Value Annotation

  • Annotation 由 compiler 計算結果, 故所有元素值必為編譯期常數量.

public @interface BaGua {

// public abstract String value
    String value() default "H3";
    String value2() default "[none]";
    int value3() default 1;
    Class<? extends String> testCase() default String.class;
    boolean yn() default false;
    enum e { HELLO, WORLD };
    String[] s();
}



Meta-Annotation




@Retention


java.lang.annotation.Retention

RetentionPolicy - 註釋保留策略。
此列舉型別的常數描述保留註釋的不同策略。它們與 Retention 元註釋型別一起使用,以指定保留多長的註釋。
列舉常數摘要
CLASS
          編譯器將把註釋記錄在類別檔案中,但在運行時 VM 不需要保留註釋。(Default)
RUNTIME
          編譯器將把註釋記錄在類別檔案中,在運行時 VM 將保留註釋,因此可以反射性地讀取。
SOURCE
          編譯器要丟棄的註釋。



java.lang.reflect
介面 AnnotatedElement

所有已知實作類別:
AccessibleObject, Class, Constructor, Field, Method, Package

public interface AnnotatedElement

表示目前正在此 VM 中運行的程序的一個已註釋元素。該介面允許反射性地讀取註釋。由此介面中的方法返回的所有註釋都是不可變並且可序列化的。調用者可以修改已賦值陣列列舉成 員的存取器返回的陣列;這不會對其他調用者返回的陣列產生任何影響。

如果此介面中的方法返回的註釋(直接或間接地)包含一個已賦值的 Class 成員,該成員參考了一個在此 VM 中不可存取的類別,則試圖通過在返回的註釋上調用相關的類別返回的方法來讀取該類別,將導致一個 TypeNotPresentException

類似地,如果註釋中的列舉常數不再以列舉型別存在,那麼試圖讀取一個已賦值的列舉成員將導致一個 EnumConstantNotPresentException

最後,閱讀其定義已經引起不相容性的成員將導致 AnnotationTypeMismatchExceptionIncompleteAnnotationException

從以下版本開始:
1.5

方法摘要
<T extends Annotation>
T
getAnnotation(Class<T> annotationClass)
          如果存在該元素的指定型別的註釋,則返回這些註釋,否則返回 null。
 Annotation[] getAnnotations()
          返回此元素上存在的所有註釋。
 Annotation[] getDeclaredAnnotations()
          返回直接存在於此元素上的所有註釋。
 boolean isAnnotationPresent(Class<? extends Annotation> annotationClass)
          如果指定型別的註釋存在於此元素上,則返回 true,否則返回 false。



@Target


java.lang.annotation
註釋型別 Target


@Documented
@Retention(value=RUNTIME)
@Target(value=ANNOTATION_TYPE)
public @interface Target

指示註釋型別所適用的程序元素的種類別。如果註釋型別宣告中不存在 Target 元註釋,則宣告的型別可以用在任一程序元素上。如果存在這樣的元註釋,則編譯器強制實施指定的使用限制。 例如,此元註釋指示該宣告型別是其自身,即元註釋型別。它只能用在註釋型別宣告上:

    @Target(ElementType.ANNOTATION_TYPE)
public @interface MetaAnnotationType {
...
}
此元註釋指示該宣告型別只可作為複雜註釋型別宣告中的成員型別使用。它不能直接用於註釋:
    @Target({}) 
public @interface MemberType {
...
}
這是一個編譯時錯誤,它表明一個 ElementType 常數在 Target 註釋中出現了不只一次。例如,以下元註釋是非法的:
    @Target({ElementType.FIELD, ElementType.METHOD, ElementType.FIELD})
public @interface Bogus {
...
}


必需元素摘要
 ElementType[] value
           
 

元素詳細資訊

value

public abstract ElementType[] value



java.lang.annotation
列舉 ElementType

java.lang.Object
繼承者 java.lang.Enum<ElementType>
繼承者 java.lang.annotation.ElementType
所有已實作的介面:
Serializable, Comparable<ElementType>

public enum ElementType
extends Enum<ElementType>

程序元素型別。此列舉型別的常數提供了 Java 程序中宣告的元素的簡單分類別。

這些常數與 Target 元註釋型別一起使用,以指定在什麼情況下使用註釋型別是合法的。

從以下版本開始:
1.5

列舉常數摘要
ANNOTATION_TYPE
          註釋型別宣告
CONSTRUCTOR
          建構子宣告
FIELD
          欄位宣告(包括列舉常數)
LOCAL_VARIABLE
          區域變數宣告
METHOD
          方法宣告
PACKAGE
          套件宣告
PARAMETER
          參數宣告
TYPE
          類別、介面(包括註釋型別)或列舉宣告



@Inherited


java.lang.annotation
註釋型別 Inherited


@Documented
@Retention(value=RUNTIME)
@Target(value=ANNOTATION_TYPE)
public @interface Inherited

指示註釋型別被自動繼承。如果在註釋型別宣告中存在 Inherited 元註釋,並且使用者在某一類別宣告中查詢該註釋型別,同時該類別宣告中沒有此型別的註釋,則將在該類別的父級類別中自動查詢該註釋型別。此過程會重複進 行,直到找到此型別的註釋或到達了該類別層次結構的頂層 (Object) 為止。如果沒有父級類別具有該型別的註釋,則查詢將指示當前類別沒有這樣的註釋。

注意,如果使用註釋型別註釋類別以外的任何事物,此元註釋型別都是無效的。還要注意,此元註釋僅促成從父級類別繼承註釋;對已實作介面的註 釋無效。




对Annotations忍耐的极限,谈谈常用框架Annotations使用感受


Comments