注解和注解处理器
什么是注解
引用《Java编程思想》第20章的注解定义:
注解(也被称为元数据)为我们在代码中添加信息提供了一种形式化的方法,使我们可以在稍后某个时刻非常方便地使用这些数据。
元注解
Java还另外提供了四种注解,专门负责新注解的创建,这些注解也被称为元注解(meta-annotation)。
| 注解 | 含义 |
|---|---|
@Target |
表示该注解可以用于什么地方。可能的 ElementType 包括:CONSTRUCTOR:构造器的声明,FIELD:域声明(包括enum实例),LOCAL_VARIABLE:局部变量声明 ,METHOD:方法声明 ,PACKAGE:包声明 ,PARAMETER:参数声明,TYPE:类、接口(包括注解类型)、或者enum声明 |
@Retention |
表示需要在什么级别保存该注解信息。可选的 RetentionPolicy 参数包括:SOURCE:注解将被编译器丢弃,CLASS:注解在class文件中可用,但会被VM丢弃,RUNTIME:VM将在运行期也保留注解,因此可以通过反射机制读取注解的信息 |
@Documented |
将此注解包含在Javadoc中。 |
@Inherited |
允许子类继承父类中的注解。 |
创建注解
1 |
|
@Target(AnnotationTarget.CLASS)表明只能在类上使用Router。@Retention(AnnotationRetention.SOURCE)表明注解的生存期是源代码编译阶段。
什么是注解处理器
注解处理器可以帮助我们事半功倍,也就是说,更少的代码(注解)神奇地变成了更多的功能。以下是注解处理器的介绍:
- 注解处理是javac内置的一个工具,用于在编译时扫描和处理注解。
- 它可以创建新的源文件;但是,它不能修改现有的。
- 它是轮流完成的。当编译到达预编译阶段时,第一轮开始。如果这一轮生成任何新文件,则下一轮以生成的文件作为其输入开始。这种情况一直持续到处理器处理完所有新文件。
javac 是java语言编程编译器。全称java compiler。javac工具读由java语言编写的类和接口的定义,并将它们编译成字节代码的class文件。
处理流程如图:
编写注解处理器
注解处理器代码
注解处理器需要在Java or Kotlin library才能使用,因此我们需要建立一个Java or Kotlin library模块。
1 | import com.bravestsnail.router.annotation.Router |
@SupportedSourceVersion指定此处理器支持 Java 8- 所有注解处理器都必须继承
AbstractProcessor类。 getSupportedAnnotationTypes()定义了该处理器在运行时查找的一组注解。如果目标模块中的任何元素都没有使用该集合中的注解进行注释,则处理器将不会运行。process是在每个注解处理轮次中调用的核心方法。- 如果一切顺利,
process必须返回true。
注册注解处理器
展开 processor ▸ src ▸ main,添加一个名为 resources 的新目录。然后在资源中添加一个子目录并将其命名为 META-INF(必须大写字母)。最后,在META-INF添加一个命名为 services的子目录。在services添加一个空文件并将其命名为 javax.annotation.processing.Processor。
文件的内容是注解处理器的全限定名称,如下
1 | com.bravestsnail.router.processor.RouterProcessor |
除了手动注册的方式外,Google提供了AutoService自动注册工具,通过以下方式依赖:
1 | implementation "com.google.auto.service:auto-service:1.2.1" |
为注解处理器添加自动注册注解
1 |
|
生成代码
通过KotlinPoet库,可以生成Kotlin代码;生成Java代码可以使用JavaPoet
扫描包下的类
[[Android 扫描包下类]]