当前位置: 首页 > news >正文

【Spring Boot】元注解

元注解

  • 1.元注解
    • 1.1 @Target
    • 1.2 @Retention
    • 1.3 @Inherited
    • 1.4 @Documented
    • 1.5 @interface
  • 2.自定义注解
    • 2.1 创建自定义注解类
    • 2.2 实现业务逻辑
    • 2.3 使用自定义注解

1.元注解

元注解就是定义注解的注解,是 Java 提供的用于定义注解的基本注解。

注解
说明
@Retention是注解类,实现声明类 Class,声明类别 Category,声明扩展 Extension
@Target放在自定义注解的上边,表明该注解可以使用的范围
@Inherited允许子类继承父类的注解,在子类中可以获取使用父类注解
@Documented表明这个注释是由 Javadoc 记录的
@interface用来自定义注释类型

1.1 @Target

该注解的作用是告诉 Java 将自定义的注解放在什么地方,比如类、方法、构造器、变量上等。它的值是一个枚举类型,有如下属性值。

  • ElementType.CONSTRUCTOR:用于描述构造器。
  • ElementType.FIELD:用于描述成员变量、对象、属性(包括 enum 实例)。
  • ElementType.LOCAL_VARIABLE:用于描述局部变量。
  • ElementType.METHOD:用于描述方法。
  • ElementType.PACKAGE:用于描述包。
  • ElementType.PARAMETER:用于描述参数。
  • ElementType.TYPE:用于描述类、接口(包括注解类型)或 enum 声明。

1.2 @Retention

该注解用于说明自定义注解的生命周期,在注解中有三个生命周期。

  • RetentionPolicy.RUNTIME:始终不会丢弃,运行期也保留该注解,可以使用反射机制读取该注解的信息。自定义的注解通常使用这种方式。
  • RetentionPolicy.CLASS:类加载时丢弃,默认使用这种方式。
  • RetentionPolicy.SOURCE:编译阶段丢弃,自定义注解在编译结束之后就不再有意义,所以它们不会写入字节码。@Override@SuppressWarnings 都属于这类注解。

1.3 @Inherited

该注解是一个标记注解,表明被标注的类型是可以被继承的。如果一个使用了 @Inherited 修饰的 Annotation 类型被用于一个 Class,则这个 Annotation 将被用于该 Class 的子类。

1.4 @Documented

该注解表示是否将注解信息添加在 Java 文档中。

1.5 @interface

该注解用来声明一个注解,其中的每一个方法实际上是声明了一个配置参数。方法的名称就是参数的名称,返回值类型就是参数的类型(返回值类型只能是基本类型、Class、String、enum)。可以通过 default 来声明参数的默认值。

定义注解格式见以下代码:

public @interface 注解名{定义体}

2.自定义注解

有时需要自定义注解来快捷地实现功能。本实例演示如何自定义注解,以及实现业务逻辑处理。

2.1 创建自定义注解类

package com.example.demo;import org.springframework.stereotype.Component;import java.lang.annotation.*;@Target({ElementType.METHOD, ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Component
public @interface MyTestAnnotation {String value();
}

代码解释如下。

  • 使用 @Target 注解标注作用范围。
  • 使用 @Retention 注解标注生命周期。
  • 使用 @Documented 将注解信息添加在 Java 文档中。

2.2 实现业务逻辑

以 AOP 的方式实现业务逻辑,见以下代码:

package com.example.demo;import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.stereotype.Component;import java.lang.reflect.Method;@Aspect
@Component
public class TestAnnotationAspect {// 拦截被 TestAnnotation 注解的方法;如果需要拦截指定 package 指定规则名称的方法,可以使用表达式 execution(...)@Pointcut("@annotation(com.example.demo.MyTestAnnotation)")public void myAnnotationPointCut() {}@Before("myAnnotationPointCut()")public void before(JoinPoint joinPoint) throws Throwable {MethodSignature sign = (MethodSignature) joinPoint.getSignature();Method method = sign.getMethod();MyTestAnnotation annotation = method.getAnnotation(MyTestAnnotation.class);// 获取注解参数System.out.print("打印TestAnnotation 参数:" + annotation.value());}}

类注解

  • @Aspect:这是一个切面注解,用于标记这个类为一个切面类。切面类包含了通知(Advice),定义了要在哪些连接点(JoinPoint)上执行的逻辑。
  • @Component:这是一个组件注解,用于将这个切面类注册为 Spring 容器中的一个组件,以便 Spring 可以自动扫描并实例化它。

切入点表达式

  • @Pointcut("@annotation(com.example.demo.MyTestAnnotation)"):这是一个切入点(Pointcut)定义,用于指定这个切面要拦截的操作。这里的切入点表达式表示拦截所有被 MyTestAnnotation 注解标记的方法。

通知方法

  • public void myAnnotationPointCut() {}:这是一个空方法,被上面的 @Pointcut 标注,用来定义切入点逻辑。

前置通知

  • @Before("myAnnotationPointCut()"):这是一个前置通知,表示在切入点 myAnnotationPointCut 指定的方法(即被 MyTestAnnotation 注解的方法)执行之前运行这个通知方法。
  • public void before(JoinPoint joinPoint) throws Throwable {...}:这是实际执行的前置通知方法。在这个方法中,可以获取到被拦截方法的签名、参数等信息,并且可以执行一些自定义的逻辑。
    • MethodSignature sign = (MethodSignature) joinPoint.getSignature();:获取方法签名。
    • Method method = sign.getMethod();:获取具体的方法对象。
    • MyTestAnnotation annotation = method.getAnnotation(MyTestAnnotation.class);:获取方法上的 MyTestAnnotation 注解。
    • System.out.print("打印TestAnnotation 参数:" + annotation.value());:打印注解的参数值。

这段代码的作用是在 Spring AOP 环境下,拦截所有使用了 MyTestAnnotation 注解的方法,并在这些方法执行之前打印出注解的参数值。这种机制可以用来做很多有趣的事情,比如 日志记录权限检查性能监控 等,极大地增强了代码的灵活性和可维护性。

2.3 使用自定义注解

在需要使用的地方使用自定义注解,直接添加注解名即可,见以下代码:

package com.example.demo;import org.springframework.context.annotation.EnableAspectJAutoProxy;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;import java.util.ArrayList;
import java.util.List;@RestController
@EnableAspectJAutoProxy
public class TestController {@RequestMapping("/")@MyTestAnnotation("测试Annotation")public void testAnnotation() {System.err.println("测试自定义注解");}}

运行上面代码,输出如下结果:

在这里插入图片描述

相关文章:

【Spring Boot】元注解

元注解 1.元注解1.1 Target1.2 Retention1.3 Inherited1.4 Documented1.5 interface 2.自定义注解2.1 创建自定义注解类2.2 实现业务逻辑2.3 使用自定义注解 1.元注解 元注解就是定义注解的注解,是 Java 提供的用于定义注解的基本注解。 注解 说明 Retention是注解…...

基于信号分解和多种深度学习结合的上证指数预测模型

大家好,我是带我去滑雪! 为了给投资者提供更准确的投资建议、帮助政府和监管部门更好地制定相关政策,维护市场稳定,本文对股民情绪和上证指数之间的关系进行更深入的研究,并结合信号分解、优化算法和深度学习对上证指数…...

基于Spring Boot的酒店住宿管理平台

1系统概述 1.1 研究背景 随着计算机技术的发展以及计算机网络的逐渐普及,互联网成为人们查找信息的重要场所,二十一世纪是信息的时代,所以信息的管理显得特别重要。因此,使用计算机来管理酒店客房管理系统的相关信息成为必然。开发…...

游聚对战平台 三国战纪2012CE修改器修改地址

游聚对战平台 三国战纪2012比较全的一次地址。 工具 ce修改器 自行百度下载 1袖箭 2褐色鸡蛋 3毒堂 4飞盘 5火焰弹 6绿色鸡蛋 7金珠 8毒蝎 9毒镖 10铁莲花 11张陵剑 12张角巾 13太清丹经 14黄石公 15九节杖 16隐身衣 17神仙笔 18 玉蜂术(效果不明)19天师…...

Qt Creator中的项目栏

shadow build: [基础]Qt Creator 的 Shadow build(影子构建)-CSDN博客 影子构建:将源码路径和构建路径分开(生成的makefile文件和其他产物都不放到源码路径),以此来保证源码路径的清洁。 实验1: 我创建了两个项目:…...

keepalived+web 实现双机热备

环境:利用keeplived实现web服务器的双机热备(高可用) 注意: (1) 利用keeplivedweb做双击热备(高可用),最少需要两台服务器,可以实现多域名对应一个VIP,并且访问不同域名,显示不同主页&#xf…...

关于python的import

在Python中,import语句用于导入其他模块或模块中的特定部分,以便在代码中使用它们。这就可以重用代码,而不是每次都从头开始编写所有的功能。 基本用法 导入整个模块: import module_name 例如: import math print(…...

帕金森后期吞咽困难:破解难题,重拾生活美味!

在这个快节奏的时代,健康成为了我们最宝贵的财富。然而,对于帕金森病患者及其家庭而言,随着病情的进展,尤其是进入后期阶段,吞咽困难成为了他们不得不面对的严峻挑战。今天,就让我们一起走进这个温暖而坚韧…...

android 添加USB网卡并配置DNS

工作需要,需要使用TBox分享的网络,Android将TBox当作一个USB网卡,接下来就简单了,配置这个网卡的信息即可。 加载默认网卡的信息在frameworks/opt/net/ethernet/java/com/android/server/ethernet/EthernetTracker.java中 Ethern…...

【面试经典150】day 8

#1024程序员节 | 征文# 作为一个未来的程序员,现在我要继续刷题了。 力扣时刻。 目录 1.接雨水 2.罗马数字转整数 3.最后一个单词的长度 4.最长公共前缀 5.反转字符串中的单词 1.接雨水 好好好好好好,一开始就接雨水。我记得接了n次了。。。 痛苦战…...

Python -- 网络爬虫

Python – 网络爬虫 流程: 1. 连接链接获取页面内容(html文件); 2. 过滤获取需要信息(正则) [可能重复步骤1,2] ; 3. 存储文件到本地。一)网络连接获取页面内容 # 网络…...

【英特尔IA-32架构软件开发者开发手册第3卷:系统编程指南】2001年版翻译,2-5

文件下载与邀请翻译者 学习英特尔开发手册,最好手里这个手册文件。原版是PDF文件。点击下方链接了解下载方法。 讲解下载英特尔开发手册的文章 翻译英特尔开发手册,会是一件耗时费力的工作。如果有愿意和我一起来做这件事的,那么&#xff…...

设计模式4 适配器 (adapter)

一句话,适配器按照客户的需求, 适配当前已有的接口。 目标接口:reqeust() public interface Target {void request(); //this is client needed interface }已有接口:specificRequest package com.example.adapter;import android.uti…...

《分布式机器学习模式》:解锁分布式ML的实战宝典

在大数据和人工智能时代,机器学习已经成为推动技术进步的重要引擎。然而,随着数据量的爆炸性增长和模型复杂度的提升,单机环境下的机器学习已经难以满足实际需求。因此,将机器学习应用迁移到分布式系统上,成为了一个不…...

【项目实战】HuggingFace初步实战,使用HF做一些小型任务

Huggingface初步实战 一、前期准备工作二、学习pipline2.1.试运行代码,使用HuggingFace下载模型2.2. 例子1,情感检测分析(只有积极和消极两个状态)2.3. 例子2,文本生成 三、学会使用Tokenizer & Model3.1.tokenizer(分词器&am…...

堆的应用——堆排序和TOP-K问题

1.堆排序 想法⼀&#xff1a; 基于已有数组建堆、取堆顶元素完成排序。也就是利用写好的堆数据结构&#xff08;之前的文章有讲解&#xff09;&#xff0c;去实现排序。 void HeapSort(int* a, int n){HP hp;for(int i 0; i < n; i){HPPush(&hp,a[i]);}int i 0;whi…...

探秘 MySQL 数据类型的艺术:性能与存储的精妙平衡

文章目录 前言&#x1f380;一、数据类型分类&#x1f380;二、整数类型&#xff08;举例 TINYINT 和 INT &#xff09;&#x1f3ab;2.1 TINYINT 和 INT 类型的定义2.1.1 TINYINT2.1.2 INT &#x1f3ab;2.2 表的操作示例2.2.1 创建包含 TINYINT 和 INT 类型的表2.2.2 插入数据…...

使用任意绘图软件自学并结合上课所学内容完成数据库原理图绘制

本次绘图采用亿图图示软件...

static、 静态导入、成员变量的初始化、单例模式、final 常量(Content)、嵌套类、局部类、抽象类、接口、Lambda、方法引用

static static 常用来修饰类的成员&#xff1a;成员变量、方法、嵌套类 成员变量 被static修饰&#xff1a;类变量、成员变量、静态字段 在程序中只占用一段固定的内存&#xff08;存储在方法区&#xff09;&#xff0c;所有对象共享可以通过实例、类访问 (一般用类名访问和修…...

基于SSM的智能养生平台管理系统源码带本地搭建教程

技术栈与架构 技术框架&#xff1a;采用SSM&#xff08;Spring Spring MVC MyBatis&#xff09;作为后端开发框架&#xff0c;结合前端技术栈layui、JSP、Bootstrap与jQuery&#xff0c;以及数据库MySQL 5.7&#xff0c;共同构建项目。 运行环境&#xff1a;项目在JDK 8环境…...

使用docker在3台服务器上搭建基于redis 6.x的一主两从三台均是哨兵模式

一、环境及版本说明 如果服务器已经安装了docker,则忽略此步骤,如果没有安装,则可以按照一下方式安装: 1. 在线安装(有互联网环境): 请看我这篇文章 传送阵>> 点我查看 2. 离线安装(内网环境):请看我这篇文章 传送阵>> 点我查看 说明&#xff1a;假设每台服务器已…...

Linux应用开发之网络套接字编程(实例篇)

服务端与客户端单连接 服务端代码 #include <sys/socket.h> #include <sys/types.h> #include <netinet/in.h> #include <stdio.h> #include <stdlib.h> #include <string.h> #include <arpa/inet.h> #include <pthread.h> …...

23-Oracle 23 ai 区块链表(Blockchain Table)

小伙伴有没有在金融强合规的领域中遇见&#xff0c;必须要保持数据不可变&#xff0c;管理员都无法修改和留痕的要求。比如医疗的电子病历中&#xff0c;影像检查检验结果不可篡改行的&#xff0c;药品追溯过程中数据只可插入无法删除的特性需求&#xff1b;登录日志、修改日志…...

AI,如何重构理解、匹配与决策?

AI 时代&#xff0c;我们如何理解消费&#xff1f; 作者&#xff5c;王彬 封面&#xff5c;Unplash 人们通过信息理解世界。 曾几何时&#xff0c;PC 与移动互联网重塑了人们的购物路径&#xff1a;信息变得唾手可得&#xff0c;商品决策变得高度依赖内容。 但 AI 时代的来…...

管理学院权限管理系统开发总结

文章目录 &#x1f393; 管理学院权限管理系统开发总结 - 现代化Web应用实践之路&#x1f4dd; 项目概述&#x1f3d7;️ 技术架构设计后端技术栈前端技术栈 &#x1f4a1; 核心功能特性1. 用户管理模块2. 权限管理系统3. 统计报表功能4. 用户体验优化 &#x1f5c4;️ 数据库设…...

搭建DNS域名解析服务器(正向解析资源文件)

正向解析资源文件 1&#xff09;准备工作 服务端及客户端都关闭安全软件 [rootlocalhost ~]# systemctl stop firewalld [rootlocalhost ~]# setenforce 0 2&#xff09;服务端安装软件&#xff1a;bind 1.配置yum源 [rootlocalhost ~]# cat /etc/yum.repos.d/base.repo [Base…...

OD 算法题 B卷【正整数到Excel编号之间的转换】

文章目录 正整数到Excel编号之间的转换 正整数到Excel编号之间的转换 excel的列编号是这样的&#xff1a;a b c … z aa ab ac… az ba bb bc…yz za zb zc …zz aaa aab aac…; 分别代表以下的编号1 2 3 … 26 27 28 29… 52 53 54 55… 676 677 678 679 … 702 703 704 705;…...

在树莓派上添加音频输入设备的几种方法

在树莓派上添加音频输入设备可以通过以下步骤完成&#xff0c;具体方法取决于设备类型&#xff08;如USB麦克风、3.5mm接口麦克风或HDMI音频输入&#xff09;。以下是详细指南&#xff1a; 1. 连接音频输入设备 USB麦克风/声卡&#xff1a;直接插入树莓派的USB接口。3.5mm麦克…...

go 里面的指针

指针 在 Go 中&#xff0c;指针&#xff08;pointer&#xff09;是一个变量的内存地址&#xff0c;就像 C 语言那样&#xff1a; a : 10 p : &a // p 是一个指向 a 的指针 fmt.Println(*p) // 输出 10&#xff0c;通过指针解引用• &a 表示获取变量 a 的地址 p 表示…...

Vue 模板语句的数据来源

&#x1f9e9; Vue 模板语句的数据来源&#xff1a;全方位解析 Vue 模板&#xff08;<template> 部分&#xff09;中的表达式、指令绑定&#xff08;如 v-bind, v-on&#xff09;和插值&#xff08;{{ }}&#xff09;都在一个特定的作用域内求值。这个作用域由当前 组件…...