JAVA之注解

注解的概述:

Java注解(Annotation)又称Java标注,是JDK5引入的一种注释机制。

Java语言中的类、构造器、方法、成员变量、参数等都可以被注解进行标注。

作用:

对Java中类、方法、成员变量做标记,然后进行特殊处理,至于到底做何种处理由业务需求来决定。

例如。JUnit框架中,标记了注解@Test的方法就可以被当成测试方法执行,而没有标记的就不能当成测试方法执行。

目录

 自定义注解:

 特殊属性:

 元注解:

 注解的解析:

注解的应用:模拟junit框架 

 自定义注解:

//格式:
Public @interface 注解名称{
    public 属性类型 属性名() default 默认值;
}
//自定义一个注解
public @interface MyBook {
    //支持很多类型
    String name();
    String [] authors();
    double price();
}
@MyBook(name = "<遇安的博客>",authors = "遇安",price = 9.9)//可以使用刚刚定义的注解,里面需要填上它所有的属性值
//可以标记类
public class 注解 {
    //可以标记构造器
    @MyBook(name = "<遇安的博客>",authors = "遇安",price = 9.9)
    private 注解(){

    }
    //可以标记方法
    @MyBook(name = "<遇安的博客>",authors = "遇安",price = 9.9)
    public static void main(String[] args) {
        //局部变量也可以标记
        @MyBook(name = "<遇安的博客>",authors = "遇安",price = 9.9)
        int age=18;
    }
}

 特殊属性:

value属性,如果只有一个value属性的情况下,使用value属性的时候可以省略value名称不写

//自定义一个注解
public @interface Book {
   String value();//特殊属性
}
//@Book(value = "/delete")//可以写上value属性名称
@Book("/delete")//也可以不写
public class 注解 {
    public static void main(String[] args) {
    }
}

但是如果有多个属性,且多个属性没有默认值,那么value名称是不能省略的,

省略便会报错。

//自定义一个注解
public @interface Book {
   String value();//特殊属性
    double price();
}
@Book(value = "/delete",price = 9.9)//当有多个属性且没有默认值的时候,不可以省略名称
public class 注解 {
    public static void main(String[] args) {
    }
}

当多个属性有默认值的时候,是可以省略名称的

//自定义一个注解
public @interface Book {
   String value();//特殊属性
    double price() default 9.9;
}
@Book("/delete")//当多个属性有默认值的时候,便可以省略名称
public class 注解 {
    public static void main(String[] args) {
    }
}

从这些案例可以看出,注解的每个属性都必须要给值,不给值便会出问题、报错

 元注解:

元注解就是注解注解的注解(写在注解上面的注解)

@Target:约束自定义注解只能在哪些地方使用。

import java.lang.annotation.ElementType;
import java.lang.annotation.Target;

//元注解
@Target({ElementType.FIELD,ElementType.METHOD})//规定可以注解成员变量和方法
public @interface MyText {

}
//@MyText//不能注解类
public class 注解 {
    //可以注解成员变量
    @MyText
    private String name;

    //可以注解方法
    @MyText
    public static void main(String[] args) {
    }
}

@Retention:申明注解的生命周期。

import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;

@Retention(RetentionPolicy.RUNTIME)//一直存在,在运行阶段这个注解也不消失
public @interface MyText {

}

 注解的解析:

注解的操作中经常需要进行解析

注解的解析就是判断是否存在注解,存在注解就解析出内容。

  • Annotation:注解的顶级接口,注解都是Annotation类型的对象
  • AnnotatedElement:该接口定义了与注解解析相关的解析方法
  • 所有的类成分Class、Method、Field、Constructor,都实现了AnnotatedElement接口,他们都拥有解析注解的能力。

注解的技巧:
注解在哪个成分上,我们就先那哪个成分对象。

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Target({ElementType.TYPE,ElementType.METHOD})//限制只能注解到类和成员方法上
@Retention(RetentionPolicy.RUNTIME)//一直存在,在运行阶段这个注解也不消失
public @interface Book {
    String value();
    double price();
    String [] author();
}

 比如注解作用在类上,则要该类的Class对象,再来拿上面的注解

import org.junit.Test;

import java.lang.reflect.Method;
import java.util.Arrays;

//完成注解的解析
public class 注解 {
    @Test
   public void get(){
       //得到类的对象
        Class c=BookStore.class;
        //判断这个类上面是否存在注解
        if(c.isAnnotationPresent(Book.class)){
            //直接获取该解析对象
            Book book= (Book) c.getDeclaredAnnotation(Book.class);
            System.out.println(book.value());
            System.out.println(Arrays.toString(book.author()));
            System.out.println(book.price());
            //运行结果:
            // <遇安的博客>
            //[遇安]
            //9.9
        }
   }
}

@Book(value = "<遇安的博客>",author = "遇安",price = 9.9)
class BookStore{

    @Book(value = "<YuAn>",author = "遇安.",price = 9.99)
    public void text(){

    }
}

 比如注解作用成员方法,则要获得该成员方法对应的Method对象,再来拿上面的注解

import org.junit.Test;

import java.lang.reflect.Method;
import java.util.Arrays;

//完成注解的解析
public class 注解 {
   @Test
   public void getMethod() throws NoSuchMethodException {
       //先得到类的对象
       Class c=BookStore.class;
       //得到方法的对象
       Method m= c.getDeclaredMethod("text");
       //判断这个类上面是否存在注解
       if(m.isAnnotationPresent(Book.class)){
           //直接获取该解析对象
           Book book= (Book) m.getDeclaredAnnotation(Book.class);
           System.out.println(book.value());
           System.out.println(Arrays.toString(book.author()));
           System.out.println(book.price());
           //运行结果:
           // <YuAn>
           //[遇安.]
           //9.99
       }
   }
}

@Book(value = "<遇安的博客>",author = "遇安",price = 9.9)
class BookStore{

    @Book(value = "<YuAn>",author = "遇安.",price = 9.99)
    public void text(){

    }
}

注解的应用:模拟junit框架 

需求:

定义若干个方法,只要加了MyTest注解,就可以在启动时被触发执行

分析:

1、定义一个自定义注解MyTest,只能注解方法,存活范围是一直都在。

2、定义若干个方法,只要有@MyTest注解的方法就能在启动时被触发执行,没有这个注解的方法不能执行。 

自定义注解类:  

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Target({ElementType.METHOD})//限制只能注解到成员方法上
@Retention(RetentionPolicy.RUNTIME)//一直存在,在运行阶段这个注解也不消失
public @interface MyTest {
}

主类:  

import java.lang.reflect.Method;

public class 注解的应用模拟junit框架 {
    @MyTest
    public void text1(){
        System.out.println("text1");
    }
    public void text2(){
        System.out.println("text2");
    }
    @MyTest
    public void text3(){
        System.out.println("text3");
    }

    //启动:有注解的才被调用
    public static void main(String[] args) throws Exception {
        注解的应用模拟junit框架 z=new 注解的应用模拟junit框架();
        //获取类对象
        Class c=注解的应用模拟junit框架.class;
        //提取全部方法
        Method [] methods=c.getDeclaredMethods();
        //遍历方法,查看是否有@MyTese注解,有就运行
        for (Method method:methods){
            if(method.isAnnotationPresent(MyTest.class)){
                //运行它
                method.invoke(z);//由方法拿对象触发自己
            }
        }
    }
    //运行结果:
    //text1
    //text3
}
  • 3
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

遇安.YuAn

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值