注解含义
个人理解就是一种带信息的标签, 即元数据,描述数据的数据, 这种数据一般不能独立运行,需要借助外部的代码或者工具才能发挥作用。使用关键字@interface定义一个注解类,本文主要用作快速熟悉的笔记
元注解
用来定义注解的基本注解
- @Retention, 指定生命周期,源代码中,字节码文件中,程序时JVM中
- RetentionPolicy.SOURCE 注解只在源码阶段保留,在编译器进行编译时它将被丢弃忽视。
- RetentionPolicy.CLASS 注解只被保留到编译进行的时候,它并不会被加载到 JVM 中。
- RetentionPolicy.RUNTIME 注解可以保留到程序运行的时候,它会被加载进入到 JVM 中,所以在程序运行时可以获取到它们
- @Documented, 生成javadoc时,该注解会被包含
- @Target, 作用范围
- ElementType.ANNOTATION_TYPE 可以给一个注解进行注解
- ElementType.CONSTRUCTOR 可以给构造方法进行注解
- ElementType.FIELD 可以给属性进行注解
- ElementType.LOCAL_VARIABLE 可以给局部变量进行注解
- ElementType.METHOD 可以给方法进行注解
- ElementType.PACKAGE 可以给一个包进行注解
- ElementType.PARAMETER 可以给一个方法内的参数进行注解
- ElementType.TYPE 可以给一个类型进行注解,比如类、接口、枚举
- @Inherited, 是否可继承
Inherited 是继承的意思,但是它并不是说注解本身可以继承,而是说如果一个超类被 @Inherited 注解过的注解进行注解的话,那么如果它的子类没有被任何注解应用的话,那么这个子类就继承了超类的注解。
@Inherited
@Retention(RetentionPolicy.RUNTIME)
@interface Test {}
@Test
public class A {}
public class B extends A {}
注解 Test 被 @Inherited 修饰,之后类 A 被 Test 注解,类 B 继承 A,类 B 也拥有 Test 这个注解
- @Repeatable, 1.8引入, 可重复的意思, 该注解可以重复出现
# Persons是一个容器注解,容器注解是用来存放其他注解的地方,本身也是一个注解
public @interface Persons {
Person[] value();
}
@Repeatable(Persons.class)
@interface Person{
String role() default "";
}
@Person(role = "coder")
@Person(role = "PM")
@Person(role = "artist")
class SuperMan{
}
注解的属性,即成员变量
注解只有成员变量,没有方法,注解的成员变量在注解的定义中以“无形参的方法”形式来声明,其方法名定义了该成员变量的名字,其返回值定义了该成员变量的类型。
# 使用default定义默认值
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
public @interface TestAnnotation {
int id();
String msg() default "";
}
使用:
# 如果注解中只有一个成员变量value,则可以省略括号不写,不设置属性值
# 如果注解的属性设置了默认值,也可以不自定义属性值
@DemoAnnotation("demo")
public class Demo {
}
java预置的注解
- @Deprecated, 用于标记过时的注解
- @Override,标记该方法要复写父类中的方法
- @SuppressWarnings,组织警告,某些代码比如调用过时的方法是编译器会告警,使用该注解忽略编译器告警
- @SafeVarargs,参数安全类型注解。它的目的是提醒开发者不要用参数做一些不安全的操作,它的存在会阻止编译器产生 unchecked 这样的警告。1.7新增
- @FunctionalInterface, 1.8新增,定义该接口为一个函数式接口
反射+注解
- isAnnotationPresent(),判断一个Class对象是否应用了某个注解
public boolean isAnnotationPresent(Class<? extends Annotation> annotationClass) {}
- getAnnotation, 指定注解类型,获取Class对象上的某个注解对象
public <A extends Annotation> A getAnnotation(Class<A> annotationClass) {}
- getAnnotations, 获取所有的注解对象
public Annotation[] getAnnotations() {}
以上为作用与类上的注解的操作方法,其他作用域的注解类似
注解作用
- 提供信息给编译器:编译器可以利用注解来探测错误和告警信息
- 编译阶段时的处理:软件工具可以利用注解信息来生成代码,HTML文档或者其他相应的处理
- 运行时的处理:某些注解可以在程序运行的时候接受代码的提取