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

springboot-Java注解(Annotation)

Java注解

是附加在代码中的一些元信息,用于一些工具在编译、运行时进行解析和使用,起到说明、配置的功能。

注解相关类都包含在java.lang.annotation包(自己设的)中。


Java注解分类

JDK基本注解

@Override:
重写父类方法,与父类不同则报错

@Deprecated

用于指示某个程序元素(如类、方法、字段等)已经过时,不推荐使用。这个注解告诉开发者,这个元素可能会在未来的版本中被移除,建议使用其他替代方案。

@SuppressWarnings(value = "unchecked") 

用于抑制编译器产生的警告。它允许开发者忽略特定的警告信息,从而避免编译输出被大量警告信息淹没。这个注解可以应用于类、方法、字段、构造函数和局部变量上。

JDK元注解

元注解用于修饰其他的注解(纪委:管干部的干部)
@Retention:定义注解的保留策略


@Retention(RetentionPolicy.SOURCE)    //注解仅存在于源码中,在class字节码文件中不包含


@Retention(RetentionPolicy.CLASS)       //默认的保留策略,注解会在class字节码文件中存,但

运行时无法获得,


@Retention(RetentionPolicy.RUNTIME)  //注解会在class字节码文件中存在,在运行时可以通过反射获取到

自定义注解 

新建一个注解文件如下:

例子:

package com.zking.ssm.annotation;

import java.lang.annotation.*;

//该文件为自定义注解
//@Retention保留策略
@Retention(RetentionPolicy.RUNTIME)
//@Target:使用位置
@Target({ElementType.TYPE,ElementType.METHOD,ElementType.PARAMETER})
//可以被文档收录
@Documented
public @interface Log {
    //default 为设置默认值
   String name() default "";
   String title() default "";
   String value() default "";
}

补充:

ElementType 枚举包括以下值:

  • TYPE:类、接口(包括注解类型)或枚举声明。
  • FIELD:字段声明(包括枚举常量)。
  • METHOD:方法声明。
  • PARAMETER:参数声明。
  • CONSTRUCTOR:构造函数声明。
  • LOCAL_VARIABLE:局部变量声明。
  • ANNOTATION_TYPE:注解类型声明。
  • PACKAGE:包声明。
  • TYPE_PARAMETER:类型参数声明(自 Java 8 起)。
  • TYPE_USE:任何类型的使用(自 Java 8 起)。

使用:

package com.zking.ssm.service.impl;

import com.zking.ssm.annotation.Log;
import com.zking.ssm.service.Userservice;
//在@Target:使用位置标注的地方直接调用即可
@Log(name = "用户业务类")
public class UserserviceImpl implements Userservice {
    //注当我们只给value赋值,则可以省略参数名
    @Log(title = "根据id查询",name = "查询")
    //@Override:重写父类方法,与父类不同则报错
    @Override
    public void findByid(@Log("参数") Integer id) {

    }
}

解析注解(难点!!!)

方式一:创建注解处理器

前提具备反射的知识

例子:给@log添加注解功能意思为在调时输出他的信息:name,title,value

package com.zking.ssm.utill;

import com.zking.ssm.service.impl.UserserviceImpl;

import java.lang.reflect.Method;

public class ReflectTest {
    public static void main(String[] args) throws Exception  {
        //java.lang.Class类--类的类
        //编程时我们是面向jdbc中api编程的(jdbc-API):由orcal,sun公司提供
        //然后当我们提供mysql驱动就可以操作MySQL(driver):产家

        //例当我们要知道某个实现类中有某些方法时,我们第一步是得到类的类对象
        //方式一:
        Class c1 = Class.forName("com.zking.ssm.service.impl.UserserviceImpl");
        //方式二:
        Class c2 = UserserviceImpl.class;
        //方式三:
        UserserviceImpl userservice = new UserserviceImpl();
        Class c3 = userservice.getClass();

        //java.lang.reflect.Method
        //getDeclaredMethods 是 Java 中 java.lang.Class 类的一个方法,
        // 用于获取当前类声明的所有方法,包括公共(public)、受保护(protected)
        // 、默认(包级私有)和私有(private)访问级别的方法,但不包括从父类继承的方法。
        Method[] methods= c1.getDeclaredMethods();
        for (Method m:methods){
            System.out.println("输出UserserviceImpl方法名="+m.getName());
        }

        //调用方法
        UserserviceImpl userservice2 = (UserserviceImpl) c1.newInstance();//得到实例
        for (Method m:methods){
            m.invoke(userservice2,1);
        }

    }
}

方式二:动态注解处理器(spring aop方式)

第一步pom文件导入依赖:

    <properties>
<!--        版本指定-->
        <spring.version>5.3.24</spring.version>
        <junit5.version>5.8.2</junit5.version>
    </properties>

    <dependencies>
<!--        依赖导入-->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context</artifactId>
            <version>${spring.version}</version>
        </dependency>

        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-aspects</artifactId>
            <version>${spring.version}</version>
        </dependency>
        <!--测试-->
        <dependency>
            <groupId>org.junit.jupiter</groupId>
            <artifactId>junit-jupiter-api</artifactId>
            <version>${junit5.version}</version>
            <scope>test</scope>
        </dependency>
    </dependencies>
package com.zking.ssm.aop;

import com.zking.ssm.annotation.Log;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.stereotype.Component;

import java.lang.reflect.Method;

@Component//注入spring容器
@Aspect//声明当前类是一个切面类
public class LogAspect {
    //@Pointcut:声明切入点
    @Pointcut("@annotation(com.zking.ssm.annotation.Log)")
    public void pointcut(){

    }
    //Before:前置通知
    @Before("pointcut()")
    //joinPoint:连接点
    public void before(JoinPoint joinPoint) throws Exception{
        System.out.println("before...");
        //signature:签名
        MethodSignature signature = (MethodSignature) joinPoint.getSignature();
        //getMethod:获取代理中的方法,得不到注解信息
        Method method = signature.getMethod();
        //joinPoint.getTarget().getClass():获取目标对象
        Method realMethod = joinPoint.getTarget().getClass()
                .getDeclaredMethod(method.getName(),method.getParameterTypes());
        Log log=realMethod.getAnnotation(Log.class);
        if (log!=null){
            System.out.println("log.name="+log.name()+",log.title="+log.title()+",log.value="+log.value());
        }
    }
}


http://www.kler.cn/a/375135.html

相关文章:

  • JWT令牌与微服务
  • 24 go语言(golang) - gorm框架安装及使用案例详解
  • es 3期 第18节-分页查询使用避坑的一些事
  • 无人设备遥控器之定向天线篇
  • Android 之 List 简述
  • 如何完全剔除对Eureka的依赖,报错Cannot execute request on any known server
  • 深入理解HTTPS协议原理
  • 闲一品交易新趋势:SpringBoot技术应用
  • 【Java SE】类型转换
  • 数据源分层开发和连接池
  • 资深项目经理推荐的这五款国产项目管理软件值得收藏使用
  • Pyhton自动化测试持续集成和Jenkins
  • maven 学习笔记:20241024
  • HJ38 求小球落地5次后所经历的路程和第5次反弹的高度
  • 使用Linux连接阿里云
  • 后端检测_文件头检测漏洞
  • 多处理机调度(李昂学长视频总结)25新增考点
  • 探索Python终端美化的终极利器:Rich库
  • SCRM系统的价格揭秘及投资回报分析
  • 边缘计算网关在机床数据采集中的应用-天拓四方
  • pandas——DataFrame
  • 多模态大模型的应用探索:多样场景下的创新实践
  • sql练习专场(一) 1-5
  • Linux·进程间通讯(管道)
  • python/Django创建应用(app)
  • 逗号运算符应用举例