注释:
jdk5.0后,Java增加了对元数据的支持。也就是Annotation(注释)。
他是是代码中的特殊标记,可以在代码编译,类加载,运行时被读取,并执行相应的处理。这样用Annotation开发在不改变原有逻辑情况下,在源文件中补充嵌入一些信息。开发工具可以通过这些信息进行验证,或部署。
Annotation提供了条为程序元素设置元数据的方法。从某些方面来看,Annotation就像修饰符一样被使用。可用于修饰包,类,成员变量,方法,参数,构造器,局部变量的声明。这些信息储存在Annotation的“name=value”对中。
注意:Annotation是一个接口。程序可以通过反射来获得指定程序元素的Annotation对象,然后通过Annotation对象获得注释里的元数据。
接下来提到的Annotation,有的是Java.lang,Annotation,有的是注释本身。
Annotation不能影响程序的执行,增加或减少Annotation,程序都一如既往得执行。如果希望程序里的Annotation发挥作用,只有通过配套的工具(Annotation Processing Tool)对Annotation里的信息访问和处理。
Annotation必须通过工具处理,工具负责处理Annotation里面包含的元数据。工具会根据里面的元数据增加额外的功能。先了解下三个Annotation的基本用法。
使用Annotation,在其前面加@,并把该Annotation当做修饰符来用,用来支持他修饰的程序元素。
@Override
@deprecated
@SuppressWarnnings
@Override修饰一个方法,指定方法覆载(告诉编译器要检查这个方法,并从父类查找是否包含了被该方法重写的方法,否则就编译错误)。强制一个子类必须覆盖覆类方法。
@deprecated
标记程序元素已过时。当其他程序使用它时,就会发出警告。
@SuppressWarnnings
刚刚介绍的是java.lang.Annotation三个基本的注释,
下面介绍自定义的Annotation,完成实际的一些功能。
定义新的Annotation用@interface
举例:定义了一个简单的Annotation
public @interface Test{
}
使用它修饰类
@Test
public class Apple<T extends Number> {
}
修改方法
import org.junit.Test;
public class Apple<T extends Number> {
@Test
public void name() {
}
}
可修饰任何程序元素,类,接口,方法等
同时带成员变量的Annotation
public @interface Test{
//注释里的成员变量以方法形式定义
String name();
int age();
}
定义了成员变量后,使用它的时候为其指定值
public class TestCircle {
@Test(age = 5, name = "小猪")
public void name() {
}
}
也可以在定义它时为它指定初始值(如果有初始化的默认值,就可以在使用时不 指定值,有了指定值,初始值就不起作用)
public @interface Test{
//注释里的成员变量以方法形式定义
String name() default "小猪";
int age() default 7;
}
根据Annotation里是否包含成员变量可以把其分成两类:
标记Annotation:不包含成员变量,如@Override
元数据Annotation:包含成员变量,因为他可以接受更多的元数据,所以叫元数据Annotation
提取Annotation信息
前面提到了java用Annotation接口来代表程序前面的注释。AnnotatedElement这个接口是所有的Annotation类型的父接口。该接口有以下几个实现类。
Class类定义
Constructor构造器定义
Package包定义
Field类的成员变量定义
Method类的方法定义
以上扩充了读取运行时Annotation的能力。当一个Annotation被定义为运行Annotation后,该注释运行时才可见,当class文件被装载时,被保存class文件里的Annotation才会被虚拟机读取。在java反射包AnnotatedElement代表了程序中可接受注释的程序元素。
程序如果通过反射获得AnnotatedElement接口实现类,可以通过调用该类的如下三个方法获得Annotation信息。
getAnnotation(Class<T> annotationClass) 获得该元素存在的指定类型的注释。
getAnnotations() 获得该元素存在的所有注释。
boolean isAnnotationPresent(Class<? extend Annotation> annotationClass)判断该程序元素是否包含了指定元素的注释。存在返回True,不存在返回false
下面是使用 Annotation举例
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.ElementType;
import java.lang.annotation.Target;
@Retention(RetentionPolicy.RUNTIME) //@Retention注释该注释在jvm运行时保留
@Target(ElementType.METHOD) //定义注解应用类
public @interface Test{
String name() default "小猪";
int age() default 5;
}
public class TestCircle {
@Test(age = 5, name = "小猪")
public void name() {
}
}
上面提到的这些注释仅仅标识程序元素,不会对程序有任何影响。为了让注释起作用,必须为注释提供一个注释处理工具。
待续....