深入理解Java注解类型(@Annotation):https://blog.csdn.net/javazejian/article/details/71860633?ops_request_misc=%257B%2522request%255Fid%2522%253A%2522164289892616780265464462%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257D&request_id=164289892616780265464462&biz_id=0&utm_medium=distribute.pc_search_result.none-task-blog-2~all~top_ulrmf~default-2-71860633.pc_search_insert_ulrmf&utm_term=%E6%B3%A8%E8%A7%A3&spm=1018.2226.3001.4187

    注解:
    一、什么是注解:是元数据,即一种描述数据的数据。

    语法格式:@注解类型名
    注解可以出现在类上、属性上、方法(包括构造方法)上、参数上等。
    注解可以出现在注解类型上。

    注解的作用:主要功能就是起到一个标识作用。比如:Spring框架如果是基于注解开发,IOC主要负责解耦,核心容器只要存放实体Bean,但是这时spring框架不知道究竟要管理哪些实体Bean,然后就可以通过spring提供的注解来进行标识,spring会启动扫描器扫描当前工程所有的类,如果发现被扫描的类有spring提供的注解,然后该类就会装载进spring容器。

    二、元注解:用来修饰注解的注解。
    在定义注解时需要通过元注解指定被修饰注解的使用场合、是否生成文档、是否可以继承、注解保持的策略。

    注解可以定义属性:包括所有基本数据类型,String,枚举
    如果一个注解指定了属性,在使用此注解时,要给属性赋值!(除非已经赋予了默认值)。
    如果属性有且仅有value,赋值时可以省略属性名。

    1. public @interface MyAnnotation {
    2. //在注解中定义属性 注意:不是方法
    3. String value();
    4. int age();
    5. double num();
    6. enum s{};
    7. }
    1. import com.jy.annotation.MyAnnotation;
    2. @MyAnnotation(value = "key",age=12,num=3.14)
    3. public class Demo01 {
    4. public static void main(String[] args) {
    5. }
    6. }

    default :注解中给属性赋予默认值的关键字。

    1. public @interface MyAnnotation {
    2. //在注解中定义属性 注意:不是方法
    3. String value() default "key";
    4. int age() default 12;
    5. double num()default 3.14;
    6. enum s{};
    7. }
    1. @MyAnnotation()
    2. public class Demo01 {
    3. public static void main(String[] args) {
    4. }
    5. }

    三、案例:
    需求:工程中如果实体Bean上有IdAnnotation注解修饰的话,在实体类中就必须含有私有的id属性,否则程序抛出异常

    class.properties

    1. classes = com.jy.pojo.Person;com.jy.pojo.User;

    User类

    1. package com.jy.pojo;
    2. import com.jy.annotation.IdAnnotation;
    3. @IdAnnotation
    4. public class User {
    5. private String name;
    6. public User(String name) {
    7. this.name = name;
    8. }
    9. public User() {
    10. }
    11. public String getName() {
    12. int i;
    13. return name;
    14. }
    15. public void setName(String name) {
    16. this.name = name;
    17. }
    18. }

    Person类

    1. package com.jy.pojo;
    2. import com.jy.annotation.IdAnnotation;
    3. @IdAnnotation
    4. public class Person {
    5. private int id;
    6. }

    Demo

    1. package com.jy.demo;
    2. import com.jy.annotation.IdAnnotation;
    3. import java.io.FileNotFoundException;
    4. import java.io.FileReader;
    5. import java.io.IOException;
    6. import java.lang.annotation.Annotation;
    7. import java.lang.reflect.Field;
    8. import java.lang.reflect.Modifier;
    9. import java.util.Properties;
    10. public class Demo01 {
    11. public static void main(String[] args) {
    12. try {
    13. FileReader fileReader = new FileReader("class");
    14. Properties properties = new Properties();
    15. properties.load(fileReader);
    16. //获取所有实体bean的全类名
    17. String classes = properties.getProperty("classes");
    18. //将字符串通过分号切割
    19. String[] split = classes.split(";");
    20. for (String s : split) {
    21. //获取字节码对象
    22. Class aClass = Class.forName(s);
    23. //获取注解,判断实体bean中是否有@IdAnnotation注解修饰
    24. Annotation annotation = aClass.getAnnotation(IdAnnotation.class);
    25. if(annotation !=null ){
    26. //根据字节码获取属性
    27. Field[] declaredFields = aClass.getDeclaredFields();
    28. for (Field declaredField : declaredFields) {
    29. if(declaredField.getName().equals("id") && Modifier.toString(declaredField.getModifiers()).contains("private")){
    30. System.out.println("该实体bean符合要求"+aClass);
    31. }else {
    32. throw new BeanIdNotFoundException("该类没有私有的id属性:"+aClass);
    33. }
    34. }
    35. }
    36. }
    37. } catch (FileNotFoundException e) {
    38. e.printStackTrace();
    39. } catch (IOException e) {
    40. e.printStackTrace();
    41. } catch (ClassNotFoundException e) {
    42. e.printStackTrace();
    43. }
    44. }
    45. }

    自定义异常:BeanIdNotFoundException

    1. package com.jy.demo;
    2. public class BeanIdNotFoundException extends RuntimeException{
    3. public BeanIdNotFoundException(String message) {
    4. super(message);
    5. }
    6. }

    四、通过反射获取注解
    Demo02

    1. package com.jy.demo;
    2. import com.jy.annotation.Filed;
    3. import com.jy.annotation.IdAnnotation;
    4. import com.jy.pojo.Person;
    5. import java.lang.reflect.Field;
    6. /**
    7. * 通过反射获取注解(很重要,spring的IOC涉及这个操作)
    8. */
    9. public class Demo02 {
    10. public static void main(String[] args) throws Exception{
    11. //获取字节码对象
    12. Class<Person> personClass = Person.class;
    13. //获取类上的注解
    14. IdAnnotation annotation = personClass.getAnnotation(IdAnnotation.class);
    15. //注解进行强转
    16. IdAnnotation idAnnotation = (IdAnnotation)annotation;
    17. //通过注解获取属性
    18. String name = idAnnotation.name();
    19. Field[] declaredFields = personClass.getDeclaredFields();
    20. for (Field declaredField : declaredFields) {
    21. Filed annotation1 = declaredField.getAnnotation(Filed.class);
    22. System.out.println(annotation1);
    23. }
    24. }
    25. }

    Filed:

    1. @Target(ElementType.FIELD)
    2. @Retention(RetentionPolicy.RUNTIME)
    3. public @interface Filed {
    4. }

    Person类

    1. @IdAnnotation
    2. public class Person {
    3. @Filed
    4. private int id;
    5. @Filed
    6. private int age;
    7. @Filed
    8. private String name;
    9. }