1. 前言
前几年我们的项目还在structs 2 上跑,有一次问一个同事是否知道Spring Boot,同事说那不是用注解来开发的吗。虽然这个答案并不完全对,但是从客观上Spring Boot对刚刚接触它的人来说最醒目的就是注解了。那么今天我们来了解一下Java语言的核心功能——注解。
2.注解是什么
public @interface Anno {
}
复制代码
以上就是一个最简单的注解声明。它可以注释到类、接口、方法以及变量上。通过向方法,接口,类或字段添加注释,为其绑定的源代码分配额外的元数据。
3.注解的用途
通过注解我们可以通知编译器有关警告和错误的信息在编译时操作源代码在运行时修改或检查行为。jdk提供内置5个基本注解来处理代码检查。
- @Override 来标记该方法重写或替换继承的方法的行为。如果你重写了父类方法不带该注解会触发一些警告。
- @SuppressWarnings 表示我们要忽略部分代码中的某些警告。如忽略潜在的类型不安全转换警告unchecked。
- @Deprecated 用来表示类、方法已经过时,不推荐使用。如果你强行使用编译器会在编译时进行警告。
- @Safevarargs 抑制“堆污染”警告。“堆污染”指的是将一个不带泛型的对象赋给带泛型的变量时引发的的类型问题。如果你不想看到该警告就可以使用该注解来抑制。
- @FunctionalInterface java 8 新增注解,只能作用于接口上来标识该接口是函数式接口。java中函数式接口表示该接口只能有一个抽象方法。如果一个接口被此注解修饰,如果添加第二个抽象方法将无法通过编译。
注解可以将一些元数据传递给你编写的逻辑。比如Spring Mvc 中的一个常用注解@RequestMapping,我们可以通过value参数来传递一个path路径,Spring Mvc通过对请求的路径的匹配来作出是否路由到该path上。 目前大量的的框架都依赖注解,比如Spring、hibernate、dubbo等等。
4.元注解
元注解是可以应用于其他注解的注解。来增强或者配置目标注解的机制。jdk目前提供了5个元注解。如果你需要开发自定义注解,请务必熟悉它们:
-
@Retention 只能用于修饰注解,来指定被修饰注解可以保留多长时间。规定了三种策略:
- RetentionPolicy.SOURCE 这种策略下被修饰的注解只能存在于源代码中,编译后被丢弃,通过反射无法获取到被修饰的注解。
- RetentionPolicy.CLASS 这种策略下被修饰的注解会被编译进字节码文件中。但是JVM无法获取到被修饰的注解。这是一个默认值,当你声明的注解没有添加任何保留策略时,会默认指定该策略。
- RetentionPolicy.RUNTIME 这种策略下被修饰的注解不但可以编译进字节码文件。而且JVM也可以获取被该注解修饰的注解。而且程序编码也可以通过反射来获取被该注解修饰的注解的一些元信息。
-
@Target 用于指定被修饰注解的修饰目标类型。如果一个注解明确了可修饰的目标类型,则只能修饰指定的类型。由枚举ElementType来规定。
- TYPE 只能修饰 类、接口、枚举。
- FIELD 只能修饰成员变量,包含枚举内的常量。
- METHOD 只能修饰方法。
- PARAMETER 只能修饰参数。
- CONSTRUCTOR 只能修饰构造器。
- LOCAL_VARIABLE 只能修饰局部变量。
- ANNOTATION_TYPE 只能修饰注解。
- PACKAGE 只能修饰包定义。也就是package-info.java中
-
TYPE_PARAMETER java 8 新增 表示该注解能写在类型参数的声明语句中。 类型参数声明如:
、 - TYPE_USE java 8 新增 注解可以再任何用到类型的地方使用。
- @Documented 被该注解修饰的注解可以被javadoc工具提取为文档。
- @Inherited 被该注解修饰的注解有继承性。这里要注意一些要点首先这种继承性体现的类之间而不是接口之间,而且注解必须是对JVM可见。也就是@Retention为RetentionPolicy.RUNTIME 才起作用。
- @Repeatable java 8 新增。在此之前在同一个元素上同一个注解只能出现一次。@Repeatable可以让一个注解多次出现在一个元素上。
5.自定义注解
自定义注解跟自定义接口类似,但是还有一些区别,实际开发你需要对自定义注解进行元注解注释。注解中的成员变量以无参抽象方法来声明,成员变量并不是所有类型都支持,目前只支持以下类型: