http://www.cnblogs.com/xdp-gacl/p/3622275.html
一萝嘁、認(rèn)識(shí)注解
注解(Annotation)很重要奋单,未來的開發(fā)模式都是基于注解的泉褐,JPA是基于注解的降允,Spring2.5以上都是基于注解的禁荸,Hibernate3.x以后也是基于注解的,現(xiàn)在的Struts2有一部分也是基于注解的了葫录,注解是一種趨勢着裹,現(xiàn)在已經(jīng)有不少的人開始用注解了,注解是JDK1.5之后才有的新特性
JDK1.5之后內(nèi)部提供的三個(gè)注解
@Deprecated 意思是“廢棄的压昼,過時(shí)的”
@Override 意思是“重寫求冷、覆蓋”
@SuppressWarnings 意思是“壓縮警告”
范例:注解的應(yīng)用:
總結(jié):注解(Annotation)相當(dāng)于一種標(biāo)記瘤运,在程序中加入注解就等于為程序打上某種標(biāo)記窍霞,沒有加,則等于沒有任何標(biāo)記拯坟,以后但金,javac編譯器、開發(fā)工具和其他程序可以通過反射來了解你的類及各種元素上有無何種標(biāo)記郁季,看你的程序有什么標(biāo)記冷溃,就去干相應(yīng)的事,標(biāo)記可以加在包梦裂、類似枕,屬性、方法年柠,方法的參數(shù)以及局部變量上凿歼。
注解就相當(dāng)于一個(gè)你的源程序要調(diào)用一個(gè)類,在源程序中應(yīng)用某個(gè)注解冗恨,得事先準(zhǔn)備好這個(gè)注解類答憔。就像你要調(diào)用某個(gè)類,得事先開發(fā)好這個(gè)類掀抹。
二虐拓、自定義注解及其應(yīng)用
自定義一個(gè)最簡單的注解:
用反射測試進(jìn)行測試AnnotationUse的定義上是否有@MyAnnotation。
三傲武、@Retention元注解
根據(jù)反射的測試的問題蓉驹,引出@Retention元注解的講解:其三種取值:RetentionPolicy.SOURCE城榛、RetentionPolicy.CLASS、RetentionPolicy.RUNTIME分別對(duì)應(yīng):Java源文件(.java文件)---->.class文件---->內(nèi)存中的字節(jié)碼
?四戒幔、 Retention注解說明
? 當(dāng)在Java源程序上加了一個(gè)注解吠谢,這個(gè)Java源程序要由javac去編譯,javac把java源文件編譯成.class文件诗茎,在編譯成class時(shí)可能會(huì)把Java源程序上的一些注解給去掉工坊,java編譯器(javac)在處理java源程序時(shí),可能會(huì)認(rèn)為這個(gè)注解沒有用了敢订,于是就把這個(gè)注解去掉了王污,那么此時(shí)在編譯好的class中就找不到注解了, 這是編譯器編譯java源程序時(shí)對(duì)注解進(jìn)行處理的第一種可能情況楚午,假設(shè)java編譯器在把java源程序編譯成class時(shí)昭齐,沒有把java源程序中的注解去掉,那么此時(shí)在編譯好的class中就可以找到注解矾柜,當(dāng)程序使用編譯好的class文件時(shí)阱驾,需要用類加載器把class文件加載到內(nèi)存中,class文件中的東西不是字節(jié)碼怪蔑,class文件里面的東西由類加載器加載到內(nèi)存中去里覆,類加載器在加載class文件時(shí),會(huì)對(duì)class文件里面的東西進(jìn)行處理缆瓣,如安全檢查喧枷,處理完以后得到的最終在內(nèi)存中的二進(jìn)制的東西才是字節(jié)碼,類加載器在把class文件加載到內(nèi)存中時(shí)也有轉(zhuǎn)換弓坞,轉(zhuǎn)換時(shí)是否把class文件中的注解保留下來隧甚,這也有說法,所以說一個(gè)注解的生命周期有三個(gè)階段:java源文件是一個(gè)階段渡冻,class文件是一個(gè)階段戚扳,內(nèi)存中的字節(jié)碼是一個(gè)階段,javac把java源文件編譯成.class文件時(shí),有可能去掉里面的注解族吻,類加載器把.class文件加載到內(nèi)存時(shí)也有可能去掉里面的注解帽借,因此在自定義注解時(shí)就可以使用Retention注解指明自定義注解的生命周期,自定義注解的生命周期是在RetentionPolicy.SOURCE階段(java源文件階段)呼奢,還是在RetentionPolicy.CLASS階段(class文件階段)宜雀,或者是在RetentionPolicy.RUNTIME階段(內(nèi)存中的字節(jié)碼運(yùn)行時(shí)階段),根據(jù)JDK提供的API可以知道默認(rèn)是在RetentionPolicy.CLASS階段 (JDK的API寫到:the retention policy defaults to RetentionPolicy.CLASS.)
下面看看@Deprecated握础、@Override辐董、@SuppressWarnings這三個(gè)注解的@Retention注解的屬性值分別是什么吧
4.1、@Deprecated
Java
API中是這樣定義的@Deprecated的
1@Documented
2 @Retention(value=RUNTIME)
3 public @interfaceDeprecated
4.2禀综、@Override
Java
API中是這樣定義的@Override的
1@Target(value=METHOD)
2 @Retention(value=SOURCE)
3 public @interfaceOverride
@Override是給javac(java編譯器)看的简烘,編譯完以后就@Override注解就沒有價(jià)值了苔严,@Override注解在源代碼中有用,編譯成.class文件后@Override注解就沒有用了孤澎,因此@Override的Retention的屬性值是RetentionPolicy.SOURCE
4.3届氢、@SuppressWarnings
Java
API中是這樣定義的@SuppressWarnings的
1@Target(value={TYPE,FIELD,METHOD,PARAMETER,CONSTRUCTOR,LOCAL_VARIABLE})
2 @Retention(value=SOURCE)
3 public @interfaceSuppressWarnings
@SuppressWarnings是給javac(java編譯器)看的,編譯器編譯完java文件后覆旭,@SuppressWarnings注解就沒有用了退子,所以@SuppressWarnings的Retention的屬性值是RetentionPolicy.SOURCE
五、@Target元注解
@Target元注解決定了一個(gè)注解可以標(biāo)識(shí)到哪些成分上型将,如標(biāo)識(shí)在在類身上寂祥,或者屬性身上,或者方法身上等成分七兜,@Target默認(rèn)值為任何元素(成分)
例如:
1 @Target(value={TYPE,FIELD,METHOD,PARAMETER,CONSTRUCTOR,LOCAL_VARIABLE})
2@Retention(value=SOURCE)
3 public @interfaceSuppressWarnings
六丸凭、為注解增加屬性
注解可以看成是一種特殊的類,既然是類腕铸,那自然可以為類添加屬性
6.1.添加屬性
語法:類型 屬性名();
其實(shí)從代碼的寫法上來看惜犀,注解更像是一種特殊的接口,注解的屬性定義方式就和接口中定義方法的方式一樣狠裹,而應(yīng)用了注解的類可以認(rèn)為是實(shí)現(xiàn)了這個(gè)特殊的接口
6.2.應(yīng)用屬性
6.3.為屬性指定缺省值(默認(rèn)值)
語法:類型 屬性名() default 默認(rèn)值;
6.4.value屬性
如果一個(gè)注解中有一個(gè)名稱為value的屬性虽界,且你只想設(shè)置value屬性(即其他屬性都采用默認(rèn)值或者你只有一個(gè)value屬性),那么可以省略掉“value=”部分酪耳。
例如:@SuppressWarnings("deprecation")
七浓恳、為注解增加高級(jí)屬性
7.1刹缝、數(shù)組類型的屬性
[if !supportLists]·????????[endif]增加數(shù)組類型的屬性:int[]arrayAttr() default {1,2,4};
[if !supportLists]·????????[endif]應(yīng)用數(shù)組類型的屬性:@MyAnnotation(arrayAttr={2,4,5})
[if !supportLists]·????????[endif]如果數(shù)組屬性只有一個(gè)值碗暗,這時(shí)候?qū)傩灾挡糠挚梢允÷源罄ㄌ?hào),如:@MyAnnotation(arrayAttr=2)梢夯,這就表示數(shù)組屬性只有一個(gè)值言疗,值為2
7.2.、枚舉類型的屬性
[if !supportLists]·????????[endif]增加枚舉類型的屬性:EumTrafficLamplamp() default EumTrafficLamp.RED;
[if !supportLists]·????????[endif]應(yīng)用枚舉類型的屬性:@MyAnnotation(lamp=EumTrafficLamp.GREEN)
7.3颂砸、注解類型的屬性
為注解添加一個(gè)注解類型的屬性,并指定注解屬性的缺省值:MetaAnnotation annotationAttr()default @MetaAnnotation("xdp");
八噪奄、注解綜合測試
EumTrafficLamp.java
MetaAnnotation.java
MyAnnotation.java
MyAnnotationTest.java