注解

  • 注释:给程序员看的,用于解释说明程序的功能
  • 注解:给程序看的,用于标识程序的运行状态。

一、注解的作用

注解是servlet3.0以后的特性,建议用注解代替XML配置文件,注解的特点及优点有:

  • 增强程序的可阅读性,相较于XML,注解紧跟方法,随时修正
  • 注解是低耦合的,

把注解应用在反射上,注解与properties配置文件的优势在于:

  • 注解可以加注释,而properties文件不可以;
  • 注解直接放在方法或类体上,更加直观和便于修改

二、注解的格式

@注解的格式,如:

JDK中提供的注解

JDK中提供的注解有三个,都是给编译器使用的,在编译时期起作用:

  • @Overrid:放在方法上一行,用于继承中复写方法的声明

    在JDK1.5版本中,只能标识由类继承的方法
    在JDK1.6版本中,可以标识接口继承的方法

  • @Deprecated:标识已过时的方法

  • @SuppressWarnings:压制警告,如SuppressWarnings(”all”)所有警告消除

三、自定义注解

自定义注解,是java的进阶应用。通过注解,并且通过注解合理的应用反射,可以构建简化的代码编写方式

  • 通过javap反编译,发现已定义的注解全部都是如下格式的继承方式:
public interface MyAno extends java.lang.annotation.Annotation {}
  • 自定义注解格式
    public @interface 注解名称{}
  • 注解中可以定义常量和抽象方法,但是定义常量没有意义,方法就相当于属性(变量);
    • 属性:其实就是接口中的抽象方法。注解的属性还可以有默认值,在使用注解时就可以不给带有默认值的属性赋值了。但没有给出默认值的属性还是要赋值的
    • 属性的类型
    • 基本数据类型
    • 字符串类型
    • 类类型:Class
    • 枚举类型
    • 注解类型
    • 以上所有的数组类型
public @interface MyAnn {
    String value() default "hello world"; 
    int value1();
}

四、元注解

用于说明注解的注解,元注解放在自定义注解的开头,有四个类型,如下:

  • @Retention : 指定注解信息在哪个阶段存在 Source Class Runtime

    • RetentionPolicy.SOURCE:这种类型的Annotations只在源代码级别保留,编译时就会被忽略
    • RetentionPolicy.CLASS:这种类型的Annotations编译时被保留,在class文件中存在,但JVM将会忽略
    • RetentionPolicy.RUNTIME:这种类型的Annotations将被JVM保留,所以他们能在运行时被JVM或其他使用反射机制的代码所读取和使用。

      @Retention(RetentionPolicy.RUNTIME) //注解保留到运行时期
      @Target({ElementType.TYPE, ElementType.METHOD}) //这是
      public @interface MyAnn {
          String value() default "hello"; 
          int value1() default 100; 
      }
      
  • @Target : 指定注解修饰目标对象类型 TYPE 类、接口 FIELD 成员变量 METHOD 方法

public @interface Target {
    ElementType[] value();
}
public enum ElementType {
TYPE,FIELD,METHOD,PARAMETED,CONSTRUCTOR,LOCAL_VARIABLE,ANNOCATION_TYPE,PACKAGE
}

这样MyAnn就只能作用在类和方法上的!其中ElementType.TYPE表示类和接口。

@Target({ElementType.TYPE, ElementType.METHOD})
public @interface MyAnn {
}
@MyAnn()
public class MyClass {
    @MyAnn() 
    private int a;

    @MyAnn()
    public void fun() {}
}
  • @Documented :使用该元注解修饰,该注解的信息可以生成到javadoc 文档中
  • @Inherited :如果一个注解使用该元注解修改,应用注解目标类的子类都会自动继承该注解

五、解析注解

当注解定义为Runtime阶段,可以使用

  • 当注解定义为Rumtime阶段,可以使用反射的方式获取注解中配置的属性值。在程序运行过程中使用。

  • 步骤:

    1.获取字节码文件。
    2.获取对象(哪个上边加了注解,获取哪个对象。如果是方法,获取Method对象)
    3.获取对象上的注解对象。
    4.调用其方法,获取返回值。

//先搞一个自定义注解,要反射一定要定义成RUNTIME
@Retention(RetentionPolicy.RUNTIME) 
@Target({ElementType.TYPE, ElementType.METHOD})
public @interface MyAnn {
    String value() default "hello";
    int value1() default 100;
}

//把注解应用到相应的类和方法上
@MyAnn(value="hello world", value1=200)
public class MyClass {
    private int a;

    @MyAnn("myMethod") 
    public void fun() {}
}

//开始使用了
public class Demo1 {
    public static void main(String[] args) throws Exception {
        //1.获得字节码文件
        Class clazz = MyClass.class;
        //2.如果是类的注解,通过getAnnotation()方法
        MyAnn myAnn = (MyAnn) clazz.getAnnotation(MyAnn.class); 
        System.out.println(myAnn.value()); 
        System.out.println(myAnn.value1()); 

        //3.如果是方法的注解,还是通过方法的字节码去获取
        Method method = clazz.getMethod("fun");
        MyAnn myAnn1 = method.getAnnotation(MyAnn.class); 
        System.out.println(myAnn1.value());
        System.out.println(myAnn1.value1());
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值