zoukankan      html  css  js  c++  java
  • java注解(基础)

    一、认识注解

    1、注解的定义:

    java提供了一种原程序中的元素关联任何信息和元数据的途径和方法。

    2、学习注解的目的:

    (1)能够读懂别人写的代码,特别是框架相关的代码(框架中使用注解是非常方便的)

    (2)让编程更加简洁,代码更为清晰。

    3、java注解分类

    (按照运行机制分)

    (1)源码注解:注解只有在源码中存在,编译成.class文件就不存在了。

    (2)编译时注解:注解在源码和.class文件中都存在

    (3)运行时注解:在运行阶段还起作用,甚至会影响运行逻辑的注解

    (按照来源分)

    (1)来自jdk的注解

    (2)来自第三方注解

    (3)我们自己定义的注解

    4、JDK注解(常见)

    (1)@Override 表明此方法覆盖了父类的方法(使用的最多)

    (2)@Deprecated 表明此方法过时了

    (3)@SuppressWarnings("deprecation") 表明忽略deprecation警告

    代码示例

     1 package Reflect;
     2 
     3  abstract class Father{
     4     public abstract String name();
     5     public abstract int age();
     6     
     7     @Deprecated//声明此方法过时
     8     public abstract void sing();
     9 }
    10 public class Test extends Father{
    11     @Override
    12     public String name() {
    13         // TODO Auto-generated method stub
    14         return null;
    15     }
    16 
    17     @Override
    18     public int age() {
    19         // TODO Auto-generated method stub
    20         return 0;
    21     }
    22 
    23     @Override//表明覆盖了父类的方法
    24     public void sing() {
    25         System.out.println("Father is singing...");
    26         
    27     }
    28     public static void main(String[] args) {
    29     
    30         @SuppressWarnings("deprecation")//表示忽略deprecation的警告
    31         Test t=new Test();
    32         t.sing();
    33         
    34     }  
    35 }

    运行结果:

    Father is singing...

    5、常见第三方注解

    spring框架、mybatis框架和hibernate框架中有大量的注解

    二、自定义注解

    1、元注解

    (1)@Target 指明注解的作用域

    @Target({ElementType.METHOD,ElemenType.TYPE})   红色部分表示作用域列表

    作用域值表

    作用域值 描述
    CONSTRUCTOR 构造方法声明
    FIELD 字段声明
    LOCAL_VARIABLE 局部变量声明
    METHOD 方法声明
    PACKAGE 包声明
    PARAMETER 参数声明
    TYPE 类、接口

    (2)@Retention  指明注解的生命周期

    @Retention(RetentionPolicy.RUNTIME)

    生命周期值表

    生命周期值 描述
    SOURCE 只在源码显示,编译时会丢弃
    CLASS 编译时会记录到class中,运行时忽略
    RUNTIME 运行时存在,可以通过反射读取

    (3)@Inherited   指明注解允许自助借来继承

    (4)@Documented   生成javadoc时会包含注解

    2、自定义注解的语法要求

    (1)成员以无参和没有异常方式声明

    (2)可以用defualt为成员指定一个默认值

    (3)成员类型是受限的,合法的类型包括原始类型(基本数据类型)及String,Class,Annotation,Enumeration。

    (4)如果注解只有一个成员,则成员名必须取名为value,在使用的时候可以忽略成员名和赋值号(=)

    (5)注解类可以没有成员,没有成员的注解称为标识注解

    代码示例:(自定义一个注解)

    package ANNOTATION;
    
    import java.lang.annotation.Documented;
    import java.lang.annotation.ElementType;
    import java.lang.annotation.Inherited;
    import java.lang.annotation.Retention;
    import java.lang.annotation.RetentionPolicy;
    import java.lang.annotation.Target;
    
    //先定义元注解的@Target坠儿,指明作用域是方法和类接口
    @Target({ElementType.METHOD,ElementType.TYPE})
    //指明注解的生命周期,运行时存在
    @Retention(RetentionPolicy.RUNTIME)
    //指明能够被子注解继承
    @Inherited
    //指明生成javadoc时会包含注解
    @Documented
    public @interface MyAnnotation {
    
        String desc();  //成员以无参和没有异常方式声明
        String author();
        int age() default 18;//可以用defualt为成员指定一个默认值
    }

    3、使用自定义注解

    使用自定义注解的语法:

    @<注解名>(<成员名1>=<成员值1>,<成员名2>=<成员值2>,....)

    代码示例:

    package ANNOTATION;
    
    @ MyAnnotation(desc="I am a boy",author="tom",age=21)
    public class AnnotationTest {
    
        @ MyAnnotation(desc="I am a girl",author="mary",age=18)
        public void girlSing(){
            System.out.println("girl is singing...");
        }
    }

    三、解析注解(读取注解中的信息,并对进行一些操作)

    概念:通过反射获取类,函数或成员变量上的运行时注解信息,从而实现动态的控制程序运行的逻辑

    注解只会继承类上的注解,当一个类去继承一个类时,可以继承该父类已有的注解,但不能继承其父类上的注解,且接口的注解不能被继承

    代码实现:

     1 package ANNOTATION;
     2 
     3 import java.lang.annotation.Annotation;
     4 import java.lang.reflect.Field;
     5 import java.lang.reflect.Method;
     6 
     7 public class Test {
     8 
     9     public static void main(String[] args) throws ClassNotFoundException {
    10         //使用类加载器加载类
    11         Class c=Class.forName("ANNOTATION.AnnotationTest");
    12         //找到类上面的注解
    13         boolean isExist=c.isAnnotationPresent(MyAnnotation.class);
    14         if(isExist){
    15         //拿到注解实例
    16         MyAnnotation m=(MyAnnotation) c.getAnnotation(MyAnnotation.class);
    17         System.out.println("类注解的信息:"+"desc:"+m.desc()+" author:"+m.author()+" age:"+m.age());
    18         }
    19         //1、获取方法上面的注解及其信息(知道方法上注解的名称)
    20         //获取类中的所有声明的方法
    21         Method[] method= c.getDeclaredMethods();
    22         for (Method method2 : method) {
    23             boolean isExist1=method2.isAnnotationPresent(MyAnnotation.class);    
    24             if(isExist1){
    25                 MyAnnotation m1=(MyAnnotation) method2.getAnnotation(MyAnnotation.class);
    26                 System.out.println(method2.getName()+"方法上注解的信息:"+"desc:"+m1.desc()+" author:"+m1.author()+" age:"+m1.age());
    27             }
    28         }
    29         //2获取方法上面的所有注解及其信息
    30         for (Method method2 : method) {
    31             //获取方法上的所有注解
    32             Annotation []at=method2.getAnnotations();    
    33             for (Annotation annotation : at) {
    34                 //开始解析MyAnnotation的成员值
    35                 if(annotation instanceof MyAnnotation){
    36                     MyAnnotation m3=(MyAnnotation) annotation;
    37                     System.out.println(method2.getName()+"方法上注解的信息:"+"desc:"+m3.desc()+" author:"+m3.author()+" age:"+m3.age());            
    38                 }
    39             }
    40             /*
    41              * 不知道方法上有哪些注释,下面代码可以获取注释的一些信息
    42              */
    43             for (Method method4 : method) {
    44                 //获取方法上的所有注解
    45                 Annotation []at1=method4.getAnnotations();    
    46                 for (Annotation annotation : at) {
    47                     //获取注解的Class类对象(反射)
    48                     Class c3=annotation.annotationType();
    49                     //打印注解的名称
    50                     System.out.println("注解名称:"+c3.getName());
    51                     //获取注解所有成员变量
    52                     Method [] m2=c3.getDeclaredMethods();
    53                     for (Method method3 : m2) {
    54                         System.out.println("注解的成员名称:"+method3.getName());
    55                     }
    56                 }
    57             }
    58         }
    59     }
    60 }

    运行结果:

    1 类注解的信息:desc:I am a boy author:tom age:21
    2 girlSing方法上注解的信息:desc:I am a girl author:mary age:18
    3 girlSing方法上注解的信息:desc:I am a girl author:mary age:18
    4 注解名称:ANNOTATION.MyAnnotation
    5 注解的成员名称:desc
    6 注解的成员名称:author
    7 注解的成员名称:age

     个人关于注解的应用理解:其实质就是对类、方法、成员变量上的注解,通过反射机制获得并进行解析,从而进一步进行操作。

  • 相关阅读:
    Docker | 第二章:第一个Docker应用
    Docker | 第一章:Docker简介
    Docker | 第零章:前言
    SpringBoot | 第十五章:基于Postman的RESTful接口测试
    SpringBoot | 第十四章:基于Docker的简单部署
    SpringBoot | 第十三章:测试相关(单元测试、性能测试)
    2014年计划
    学习方法,工作方法 探讨
    2013年总结
    asp.net用Zxing库实现条形码输出
  • 原文地址:https://www.cnblogs.com/xiaotiaosi/p/6403306.html
Copyright © 2011-2022 走看看