定義
注解(Annotation),也叫元數(shù)據(jù)互纯,是一種代碼級別的說明。它是JDK1.5及以后版本引入的一個特性磕蒲,與類留潦、接口、枚舉是在同一層次辣往。它可以聲明在包兔院、類、字段站削、方法坊萝、局部變量、方法參數(shù)许起、構(gòu)造函數(shù)等的前面十偶,用來對這些元素進(jìn)行說明和注釋。
元注解
元注解的作用就是負(fù)責(zé)注解其他注解园细,即注解的注解惦积。Java5.0定義了4個標(biāo)準(zhǔn)的meta-annotation類型,它們被用來提供對其他annotatio類型作說明猛频。Java5.0定義的元注解:@Retention狮崩、@Target蛛勉、@Documented、@Inherited
@Retention
@Retention表示需要在什么級別保存該注釋信息睦柴,用于描述注解的生命周期诽凌,取值有
? ? ? ? ? ? ?1、@Retention(RetentionPolicy.SOURCE)? 注解僅存在于源碼中坦敌,在class字節(jié)碼文件中不包含
? ? ? ? ? ? ?2侣诵、@Retention(RetentionPolicy.CLASS) ?默認(rèn)的保留策略,注解會在class字節(jié)碼文件中存在恬试,但運(yùn)行時無法獲得
? ? ? ? ? ? ?3窝趣、@Retention(RetentionPolicy.RUNTIME) 注解會在class字節(jié)碼文件中存在,在運(yùn)行時可以通過反射獲取到
SOURCE 例1
自定義注解MyAnnotation,Retention的取值是保留策略的SOURCE
@Retention(RetentionPolicy.SOURCE)
public ?@interface ?MyAnnotation{
}
標(biāo)注的類Test
@MyAnnotation
public classTest {
? ? ? ? ? ?public static void main(String[] args) {
? ? ? ? ? ? ? ? ? ? ? ? ? ? ?System.out.println("生成的class文件反編譯后不會出現(xiàn)注解@MyAnnotation");
? ? ? ? ? ? }
}
反編譯生成的.class文件训柴,Test類不存在MyAnnotation注解
CLASS 例2
自定義注解MyAnnotation,Retention的取值是保留策略的CLASS
@Retention(RetentionPolicy.CLASS)
public ?@interface ?MyAnnotation{
}
標(biāo)注的類Test
@MyAnnotation
public classTest {
? ? ? ? ? ? ? ?public static void ?main(String[] args) {
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? System.out.println("生成的class文件反編譯后會出現(xiàn)注解@MyAnnotation");
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? Annotation[] annotations = Test.class.getAnnotations();
? ? ? ? ? ? ? ? ? ? ? ? ? ? ?System.out.println("Runtime期間標(biāo)注在Test類上的注解個數(shù)為:"+ annotations.length);
? ? ? ? ? ? ? ? ?}
}
驗證結(jié)果:.class文件出現(xiàn)注解哑舒,運(yùn)行期間獲取Test類上的注解個數(shù)為0
RUNTIME 例2
自定義注解MyAnnotation,Retention的取值是保留策略的RUNTIME
@Retention(RetentionPolicy.RUNTIME)
public? @interface? MyAnnotation{
}
標(biāo)注的類Test
@MyAnnotation
public classTest {
? ? ? ? ? ? ?public static void ?main(String[] args) {
? ? ? ? ? ? ? ? ? ? ? ? ? ? System.out.println("生成的class文件反編譯后會出現(xiàn)注解@MyAnnotation");
? ? ? ? ? ? ? ? ? ? ? ? ? ? Annotation[] annotations = Test.class.getAnnotations();
? ? ? ? ? ? ? ? ? ? ? ? ? ? System.out.println("Runtime期間標(biāo)注在Test類上的注解個數(shù)為:"+ annotations.length);
? ? ? ? ? ? ? }
}
驗證結(jié)果:.class文件出現(xiàn)注解,運(yùn)行期間獲取Test類上的注解個數(shù)為1
@Target
用于設(shè)定注解使用范圍幻馁,通過ElementType來指定可使用范圍的枚舉集合洗鸵。
注解只能在ElementType設(shè)定的范圍內(nèi)使用,否則將會編譯報錯仗嗦。
@Documented
@Documented標(biāo)注的注解應(yīng)該被javadoc工具記錄膘滨。默認(rèn)情況下,javadoc是不包括注解的稀拐,如果聲明注解時指定了@Documented,注解類型信息也會被包括在生成的文檔中火邓。
@Inheried
@Inherited:允許子類繼承標(biāo)注在父類上的注解。
package-info.java
package-info.java不是平常類德撬,其作用有三個:
? ? ? ? ? 1.為標(biāo)注在包上Annotation提供便利
? ? ? ? ? ?2.聲明包的私有類和常量
? ? ? ? ? ?3. 提供包的整體注釋聲明
package-info.java里不能聲明public class 或 public interface铲咨,在package-info.java定義的類和普通類沒什么卻別。
例子 1
MyPackageAnnotation
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.PACKAGE)
@Documented
public@interfaceMyPackageAnnotation{
? ? ? ? ? String version()default"";
}
package-info.java
@MyPackageAnnotation(version ="1.0")
packagecom.leeem.domain;
importcom.leeem.annotation.MyPackageAnnotation;
//類方法
classPackageClass{
? ? ? ? ? ?public voidclassMethod(){
? ? ? ? ? ? ? ? ? ? ? ? System.out.println("class method");
? ? ? ? ? ?}
}
//類常量字段
classPackageClassConstant{
? ? ? ? ? ? ? public static finalStringERROR_CODE="100001";
}
//接口方法
interfacePackageInterface{
? ? ? ? ? public voidinterfaceMethod();
}
Test.java ?--獲取包注解
public classTest {
? ? ? ? ? ? ? ? ? ? ?public static voidmain(String[] args) {
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? Package p = Package.getPackage("com.leeem.domain");
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? MyPackageAnnotationmyPackageAnnotation = p.getAnnotation(MyPackageAnnotation.class);
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? if(myPackageAnnotation !=null&& p.isAnnotationPresent(MyPackageAnnotation.class)){
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? System.out.println("獲取到包注解蜓洪,且版本version為:"+ myPackageAnnotation.version());
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?}
? ? ? ? ? ? ? ? ? ? ? }
}
輸出:獲取到包注解纤勒,且版本version為:1.0
Test.java ?--使用package-info.java定義的類 (接口類似)
public classTest {
? ? ? ? ? ? ? ? public static voidmain(String[] args) {
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? PackageClasspackageClass =newPackageClass();
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? packageClass.classMethod();
? ? ? ? ? ? ? ? ? }
}
輸出:class method
Test.java? --使用package-info.java定義的類的常量
public classTest {
? ? ? ? ? ? ? ?public static voidmain(String[] args) {
? ? ? ? ? ? ? ? ? ? ? ? ? ? ?System.out.println(PackageClassConstant.ERROR_CODE);
? ? ? ? ? ? ? ?}
}
輸出:100001
Java內(nèi)置注解
Java SE5內(nèi)置了三種標(biāo)準(zhǔn)注解:@Override、@Deprecated隆檀、@SuppressWarnings
@Override:表示當(dāng)前的方法定義將覆蓋超類中的方法摇天。
@Deprecated:標(biāo)注已過時或已廢棄的代碼,通常存在更好的選擇恐仑。使用該注解標(biāo)注的元素時泉坐,編譯器會報警
@SuppressWarnings:用來抑制編譯時的警告信息