注解

发布时间 2023-12-19 10:33:04作者: 梅丹隆

可以使用注解来保存类的相关信息以供反射调用
image.png

1、简介

提供一种为程序元素设置元数据的方法

  • 元数据是添加到程序元素(如:方法、字段、类和包)上的额外信息
  • 注解是一种分散式的元数据设置方式,XML是集中时的设置方式
  • 注解不能直接干扰程序代码的运行

2、功能

  1. 作为特定的标记,用于告诉编译器一些信息
  2. 编译时动态处理,如动态生成代码
  3. 运行时动态处理,作为额外信息的载体,如获取注解信息

3、分类

  1. 标准注解:Override、Deprecated、SuppressWarnings
  2. 元注解:Retention、Target、Inherited、Documented
  3. 自定义注解

3.1、元注解

用于修饰注解的注解,通常用在注解的定义上

3.1.1、Target

注解的作用目标
使用范围:

  1. packages、types(类、接口、枚举、Annotation类型)
    1. TYPE_PARAMETER--作用在范型类的实参之上
    2. PARAMETER--作用在普通参数上
  2. 类型成员(方法、构造方法、成员变量、枚举值)
  3. 本地参数和本地变量(如循环变量、catch参数)

3.1.2、Retention

标注注解被保留时间的长短,用于定义注解的生命周期
RetentionPolicy:

  1. SOURCE:只标记源代码,不会被编译到class文件中
  2. CLASS:源代码 + class文件
  3. RUNTIME:运行时有效

3.1.3、Documented

注解是否应当被包含在JavaDoc文档中(默认注解是不会被编译在JavaDoc中的)

3.1.4、Inherited

是否允许子类继承该注解

4、自定义注解

public @interface 注解名 {
    修饰符 返回值 属性名() 默认值;
    修饰符 返回值 属性名() 默认值;
    ...
}

:::warning
注意:
1注解无法继承和实现接口的
2、修饰符不可用private和protected修饰
:::

4.1、注解属性支持的类型:

  1. 所有的基本数据类型:int,float,boolean,byte,double,char,long,short
  2. String类型
  3. Class类型
  4. Enum类型
  5. Annotation类型
  6. 以上所有类型的数组

4.2、注解底层实现

  • JVM会为注解生成代理对象
    • IDEA启动设置 VM options:
      • 记录注解代理对象:-Djdk.proxy.ProxyGeneratedFiles=true
      • 跟踪类加载:-XX:+TraceClassLoading

4.3、注解工作原理

  1. 通过简直对的形式为注解属性赋值
    1. image.png
  2. 编译器检查注解的使用范围,将注解信息写入元素属性表
  3. 运行时JVM将RUNTIME的所有注解属性取出并最终存入map里
  4. 创建AnnotationInvocationHandler实例并擦混入前面的map
  5. JVM使用JDK动态代理为注解生成代理类,并初始化处理器
  6. 调用invoke方法,通过传入方法名返回直接对应的属性值

参考
Spring源码轻松学 一课覆盖Spring核心知识点