元註解——java.lang.annotation.Target(1.8)

null^發表於2017-12-05

參考資料:https://docs.oracle.com/javase/8/docs/api/java/lang/annotation/Target.html

普通註解’只能用來註解’程式碼’,而’元註解’只能用來註解 ‘普通註解’。

@Target:限制註解的元素種類。

不加元註解@Target的情況下,註解可以修飾各種元素,比如可以修飾類,可以修飾變數,可以修飾方法等,但是如果要限制註解的元素種類,則需要加入@Target。

原始碼:

package java.lang.annotation;

/**
 * Indicates the contexts in which an annotation type is applicable. The
 * declaration contexts and type contexts in which an annotation type may be
 * applicable are specified in JLS 9.6.4.1, and denoted in source code by enum
 * constants of {@link ElementType java.lang.annotation.ElementType}.
 *
 * <p>If an {@code @Target} meta-annotation is not present on an annotation type
 * {@code T} , then an annotation of type {@code T} may be written as a
 * modifier for any declaration except a type parameter declaration.
 *
 * <p>If an {@code @Target} meta-annotation is present, the compiler will enforce
 * the usage restrictions indicated by {@code ElementType}
 * enum constants, in line with JLS 9.7.4.
 *
 * <p>For example, this {@code @Target} meta-annotation indicates that the
 * declared type is itself a meta-annotation type.  It can only be used on
 * annotation type declarations:
 * <pre>
 *    &#064;Target(ElementType.ANNOTATION_TYPE)
 *    public &#064;interface MetaAnnotationType {
 *        ...
 *    }
 * </pre>
 *
 * <p>This {@code @Target} meta-annotation indicates that the declared type is
 * intended solely for use as a member type in complex annotation type
 * declarations.  It cannot be used to annotate anything directly:
 * <pre>
 *    &#064;Target({})
 *    public &#064;interface MemberType {
 *        ...
 *    }
 * </pre>
 *
 * <p>It is a compile-time error for a single {@code ElementType} constant to
 * appear more than once in an {@code @Target} annotation.  For example, the
 * following {@code @Target} meta-annotation is illegal:
 * <pre>
 *    &#064;Target({ElementType.FIELD, ElementType.METHOD, ElementType.FIELD})
 *    public &#064;interface Bogus {
 *        ...
 *    }
 * </pre>
 *
 * @since 1.5
 * @jls 9.6.4.1 @Target
 * @jls 9.7.4 Where Annotations May Appear
 */
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.ANNOTATION_TYPE)
public @interface Target {
    /**
     * Returns an array of the kinds of elements an annotation type
     * can be applied to.
     * @return an array of the kinds of elements an annotation type
     * can be applied to
     */
    ElementType[] value();
}
View Code

指定註釋型別適用的上下文。即:用於設定註解的使用範圍(被描述的註解可以用在什麼地方)。

在JLS 9.6.4.1中規定了註解型別可能適用的宣告上下文和型別上下文,並且在原始碼中用java.lang.annotation.ElementType的列舉常量表示。即:Target用ElementType來指定註解可使用範圍的列舉集合。

如果註解型別T中不存在@Target元註釋,則宣告的註解型別T可被用於除了型別引數宣告之外的任何宣告的修飾符。即,如果註釋型別宣告中不存在 Target 元註釋,則宣告的型別可以用在任一程式元素上 。

如果存在@Target元註釋,則編譯器將強制執行由ElementType列舉常量指定的使用限制。

例如:這個@Target元註釋表明宣告的型別本身就是一個元註釋型別。它只能用於註解型別宣告:

    @Target(ElementType.ANNOTATION_TYPE)
    public @interface MetaAnnotationType {
        ...
    }

這個@Target元註釋表明,宣告的型別僅用作複雜註釋型別宣告中的成員型別。它不能用來直接註解任何東西。

    @Target({})
    public @interface MemberType {
        ...
    }

單個ElementType常量在@Target註釋中出現多次是編譯時錯誤,例如,下面的元註釋是非法的:

    @Target({ElementType.FIELD, ElementType.METHOD, ElementType.FIELD})
    public @interface Bogus {
        ...
    }

ElementType[]:

  返回註釋型別可用的各種元素陣列。

   取值有:

    TYPE:類、介面(包括註解型別) 或enum宣告。

    FIELD:欄位宣告(包括enum常量).

    METHOD:方法宣告。

    PARAMTER:形式引數宣告。

    CONSTRUCTOR:建構函式宣告。

    LOCAL_VARIABLE:區域性變數宣告。

    ANNOTATION_TYPE:註解型別宣告。

    PACKAGE:包宣告

    TYPE_PARAMETER:引數型別宣告

    TYPE_USE:使用一個型別,詳見:java.lang.annotation.ElementType

相關文章