java註解與APT技術
1,基本概念
什麼是註解?
註解(Annotation),也叫元資料。一種程式碼級別的說明。它是JDK1.5及以後版本引入的一個特性,與類、介面、列舉是在同一個層次。它可以宣告在包、類、欄位、方法、區域性變數、方法引數等的前面,用來對這些元素進行說明,註釋。
什麼是元註解?
簡單來說,就是註解的註解,元註解的作用就是負責註解其他註解。Java5.0定義了4個標準的meta-annotation型別,它們被用來提供對其它 annotation型別作說明:
[email protected],
[email protected],
[email protected],
4.[email protected]
下面我們看一下每個元註解的作用和相應分引數的使用說明。
- @Target:
該標識用於描述註解的使用範圍(即:被描述的註解可以用在什麼地方): packages、types(類、介面、列舉、Annotation型別)、型別成員(方法、構造方法、成員變數、列舉值)、方法引數和本地變數(如迴圈變數、catch引數)。在Annotation型別的宣告中使用了target可更加明晰其修飾的目標。
取值(ElementType)有:
1.CONSTRUCTOR:用於描述構造器
2.FIELD:用於描述域
3.LOCAL_VARIABLE:用於描述區域性變數
4.METHOD:用於描述方法
5.PACKAGE:用於描述包
6.PARAMETER:用於描述引數
7.TYPE:用於描述類、介面(包括註解型別) 或enum宣告
- @Retention:
該標示定義了該Annotation被保留的時間長短:某些Annotation僅出現在原始碼中,而被編譯器丟棄;而另一些卻被編譯在class檔案中;編譯在class檔案中的Annotation可能會被虛擬機器忽略,而另一些在class被裝載時將被讀取(請注意並不影響class的執行,因為Annotation與class在使用上是被分離的)。
取值(ElementType)有:
1.SOURCE:在原始檔中有效(即原始檔保留)
2.CLASS:在class檔案中有效(即class保留)
3.RUNTIME:在執行時有效(即執行時保留)
@Documented:
Documented用於描述其它型別的annotation應該被作為被標註的程式成員的公共API,因此可以被例如javadoc此類的工具文件化。Documented是一個標記註解,沒有成員@Inherited:
@Inherited 元註解是一個標記註解,@Inherited闡述了某個被標註的型別是被繼承的。如果一個使用了@Inherited修飾的annotation型別被用於一個class,則這個annotation將被用於該class的子類。注意:@Inherited annotation型別是被標註過的class的子類所繼承。類並不從它所實現的介面繼承annotation,方法並不從它所過載的方法繼承annotation。
當@Inherited annotation型別標註的annotation的Retention是RetentionPolicy.RUNTIME,則反射API增強了這種繼承性。如果我們使用java.lang.reflect去查詢一個@Inherited annotation型別的annotation時,反射程式碼檢查將展開工作:檢查class和其父類,直到發現指定的annotation型別被發現,或者到達類繼承結構的頂層。
自定義註解
定義註解格式:
public @interface 註解名 {定義體}
使用@interface自定義註解時,自動繼承了java.lang.annotation.Annotation介面,由編譯程式自動完成其他細節。在定義註解時,不能繼承其他的註解或介面。@interface用來宣告一個註解,其中的每一個方法實際上是聲明瞭一個配置引數。方法的名稱就是引數的名稱,返回值型別就是引數的型別(返回值型別只能是基本型別、Class、String、enum)。可以通過default來宣告引數的預設值。
註解引數的可支援資料型別:
1.所有基本資料型別(int,float,boolean,byte,double,char,long,short)
2.String型別
3.Class型別
4.enum型別
5.Annotation型別
6.以上所有型別的陣列
Annotation型別裡面的引數設定:
第一,只能用public或預設(default)這兩個訪問權修飾.例如,String value();這裡把方法設為defaul預設型別;
第二,引數成員只能用基本型別byte,short,char,int,long,float,double,boolean八種基本資料型別和 String,Enum,Class,annotations等資料型別,以及這一些型別的陣列.例如,String value();這裡的引數成員就為String;
第三,如果只有一個引數成員,最好把引數名稱設為”value”,後加小括號.例:下面的例子FruitName註解就只有一個引數成員。
註解引數的可支援資料型別:
1.所有基本資料型別(int,float,boolean,byte,double,char,long,short)
2.String型別
3.Class型別
4.enum型別
5.Annotation型別
6.以上所有型別的陣列
Annotation型別裡面的引數該怎麼設定:
第一,只能用public或預設(default)這兩個訪問權修飾.例如,String value();這裡把方法設為defaul預設型別;
第二,引數成員只能用基本型別byte,short,char,int,long,float,double,boolean八種基本資料型別和 String,Enum,Class,annotations等資料型別,以及這一些型別的陣列.例如,String value();這裡的引數成員就為String;
第三,如果只有一個引數成員,最好把引數名稱設為"value",後加小括號.
下面是一個簡單的自定義註解的栗子:
package annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* 動物名稱註解
*
*/
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface AnimalName {
String value() default "";
}
定義了註解,並在需要的時候給相關類,類屬性加上註解資訊,如果沒有響應的註解資訊處理流程,註解可以說是沒有實用價值,接下來要介紹的是java的APT(Annotation Process Tool)技術,用於處理自定義註解。
2,APT技術
APT(Annotation Process Tool),是一種在程式碼編譯時處理註解,按照一定的規則,生成相應的java檔案,多用於對自定義註解的處理,目前比較流行的Dagger2, ButterKnife, EventBus3都是採用APT技術,對執行時的效能影響很小。我們通過自定義註解的方式,來了解一下如何使用APT:
1,自定義註解:
@Target({ElementType.TYPE}) ---作用範圍 Class
@Retention(RetentionPolicy.CLASS) ---生命週期:僅保留到.class檔案
public @interface Route {
/** Path of route*/
String value(); ---類似於成員變數
}
2,使用方式
@Route(path = "/test/activity2")
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_test2);
}
}
JVM預設只會處理@override等語言自帶的註解,對於自定義的註解,需要我們自己處理,java提供了一個名為AbstractProcessor.java的抽象類,我們只要繼承該類,就實現自己的註解處理器,來處理自定義的@Route註解
public class RouteProcessor extends AbstractProcessor {
@Override
public synchronized void init(ProcessingEnvironment env){
// 主要做一些初始化操作
}
@Override
public boolean process(Set<? extends TypeElement> annoations, RoundEnvironment env) {
//具體處理註解的邏輯,控制程式碼的生成
processAnnotations();
}
@Override
public Set<String> getSupportedAnnotationTypes() {
// 支援處理的註解型別, 在這裡就是@Route
}
@Override
public SourceVersion getSupportedSourceVersion() {
//java版本 如:jdk1.6or jdk1.7
}
}
3,自定義Processor
@AutoService(Processor.class)
public class HelloProcessor extends AbstractProcessor {
/** 檔案相關的輔助類 用於生成新的原始檔、class等 */
private Filer mFiler;
@Override
public synchronized void init(ProcessingEnvironment processingEnv) {
super.init(processingEnv);
mFiler = processingEnv.getFiler();
}
@Override
public boolean process(Set<? extends TypeElement> annotations, RoundEnvironment roundEnv) {
// 構建方法 此處使用到了square公司的javapoet庫,用來輔助生成 類的程式碼
MethodSpec.Builder methodBuilder = MethodSpec.methodBuilder("show")
.addModifiers(Modifier.PUBLIC);
methodBuilder.addStatement("String test = \"$N\" ","hello annotation world!");
/** 構建類 */
TypeSpec finderClass = TypeSpec.classBuilder("Hello$$Inject")
.addModifiers(Modifier.PUBLIC)
.addMethod(methodBuilder.build())
.build();
try {
JavaFile.builder("com.win.test",finderClass).build().writeTo(mFiler);
} catch (IOException e) {
e.printStackTrace();
}
return true;
}
// 支援的註解型別
@Override
public Set<String> getSupportedAnnotationTypes() {
Set<String> types = new LinkedHashSet<>();
types.add(Hello.class.getCanonicalName());
return types;
}
@Override
public SourceVersion getSupportedSourceVersion() {
return super.getSupportedSourceVersion();
}
}
在AS工程中使用
@Hello("MainTest") //自定義的Hello註解
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
}
在專案App module的build目錄下,便會生成對應的java類檔案:
這個只是簡單的栗子,我們可以在process()方法中,加入更多的業務邏輯,以實現特定功能。
相關推薦
[轉]java註解與APT技術
pretty runt src ons data exception clas -m animal 下面是一個簡單的自定義註解的栗子: package annotation; import java.lang.annotation.Docume
java註解與APT技術
1,基本概念 什麼是註解? 註解(Annotation),也叫元資料。一種程式碼級別的說明。它是JDK1.5及以後版本引入的一個特性,與類、介面、列舉是在同一個層次。它可以宣告在包、類、欄位、方法、區域性變數、方法引數等的前面,用來對這些元素進行說
Java註解與反射應用的小例子
1.功能介紹 小例子主要完成以下功能,通過Java反射獲取SQL語句,使用MyBatis傳入SQL語句,將資料插入到資料庫中2.程式碼講解2.1 自定義註解 首先看一個自定義註解,在此例子中我自定義了兩個註解,一個叫DBTable,另一個是DBColumn。
[java][annotation][@Aspect]Java註解與切面使用
import org.springframework.kafka.annotation.KafkaListener; impor
Spring註解與Java元註解小結
spa package param style 值範圍 描述 tro ret 類型 註解 Annotation 基於註解的開發,使得代碼簡潔,可讀性高,簡化的配置的同時也提高了開發的效率,尤其是SpringBoot的興起,隨著起步依賴和自動配置的完善,更是將基於註解的開發推
Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰(資源同步)
第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級資料進行壓力測試。讓大
6. Spring:Java註解技術詳解
6. Spring:Java註解技術詳解 自定義註解示例:https://blog.csdn.net/wangpengzhi19891223/article/details/78131137/ Java註解技術基本概念 Annotation是Java5開始引入的新特徵。中文
Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰(無密連結)
第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級資料進行壓力測試。讓大
Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰
Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰 第1章 課程介紹 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後
#Java怎麼學?2018最新Java學習路線,技術要求與專案推薦詳解!
一 基礎篇 很多人認為,java的基礎應該是C語言,這個不可否認,但是也不能說完全正確,因為兩個語言技術的內涵是不一樣的,C語言是面向語言程式設計而java語言是面向物件程式設計,打個比喻,C語言大多數是做系統應用,而java是做企業級應用的。所以,學Java不一定要學C,Java簡化了C,而在
Python自動生成10000個java類使用APT註解後引發的問題!
前言 前面寫了一篇關於自己開發的一個 基於APT註解的用於RecyclerView複雜樓層的開源框架 ,框架的原理比較簡單,通過註解,在編譯期會生成一個ComponentRule.java的檔案,然後建立一個對映關係。使用方式簡單介紹一下: 1.繫結佈局檔案 @ComponentType
某課最新Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰
第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級
某課最全Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰
第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級
阿里專家與你分享:你必須瞭解的Java多執行緒技術
摘要: 本文介紹了Lambda表示式的起源以及基本語法,並提供程式碼例項幫助大家理解Lambda表示式的使用。另外,本文介紹了Java開發中常用的多執行緒技術,詳細介紹多執行緒涉及到的概念以及使用方法。 數十款阿里雲產品限時折扣中,趕緊點選這裡,領劵開始雲上實踐吧! 演講
2018最新Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰(已完結)
第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級資料進行壓力測試。讓大
閒談java中的程式編譯與優化技術
java中的程式編譯和優化技術同其他語言一樣基本都發生在編譯期。java的編譯期可根據不同的編譯器分為三個部分,一個是前端編譯器,比如javac;它的工作就是把.java檔案轉化為.class檔案。另一個是即時編譯器,比如JIT編譯器;它的工作是把.class檔案中的某些
某課無加密Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰
第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級
Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰(雲盤分享)
第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級
某網Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰(雲盤下載)
第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級
Android進階——Java註解實戰之APT構建模組化的第一步
前言 APT的學習要花點時間去掌握和實踐的,短時間內只能掌握知識點,更多的是在實戰中去實踐。其實,APT就是一種工具而已,只要用多了,自然就會熟練了,不過要想實踐之前,還是必須把基礎知識學好才能實戰進入開發。文章會從基礎用例講解知識點,然後再通過實戰進行實踐 APT簡介 AP