Java Annotations详解
CSDN博客
· · 68 次点击 ·
·
开始浏览
Java注释被用来为java代码提供元数据(meta data)。作为元数据,注释不会直接影响代码的执行结果,不过事实上有些注释就是为了影响代码的执行结果而定义的。
Java注释是从Java 5开始添加的。本文对于Java注释的讨论是基于java 6的,据我所知,到目前为止Java 7中关于注释的部分并没有发生改变,所以本文对java 7编程人员上来说应该也是可用的。
目录:
· Java 注释的作用
· 注释的基础知识
· 注释的位置
· Java中预置的注释
· 创建你自己的注释
Java 注释的作用
预编译指令(Compiler instructions)
编译时指令(Build-time instructions)
运行时指令(Runtime instructions)
Java有三个编译注释,你可以使用它们来给编译器发送指令。这些注释会在稍后再做更详细的介绍。
Java注释可以在编译时(build-time)时使用,当你编译你的工程时。编译过程包括生成源代码,编译资源文件,生成XML文件(如:部署表述文件),以及将编译好的代码或文件打包成一个jar文件等。编译过程通常是由诸如Apache Ant或Apache Maven之类的编译工具自动完成的。编译工具会浏览你代码中的特定注释,并基于这些注释生成源代码或其他文件。
通常情况下,Java注释在代码编译完成后就变得不可见了。但是存在这种可能,你可以定义自己的注释,并使它们在运行时仍然可见。之后可以通过反射机制来访问这些注释来影响你的程序。
注释的基本知识
注释的最简单形式如下:
@Entity
字符@告诉编译器这是一个注释,后面的Entity表示该注释的名称。
注释的元素
一个注释可以包含多个可以被赋值的元素。一个元素就像是一个属性或者参数。下面是一个包含一个元素的注释
@Entity(tableName = "vehicles")
元素紧跟在注释之后,并放置在圆括号中,没有元素的注释,不需要圆括号。注释可以包含多个元素,当只包含一个元素时,可以省略元素名,只提供元素值既可,如下:
@InsertNew("yes")
注释的位置
你可以将注释放置到类、接口、方法、方法参数、成员变量、局部变量之前。下面是一个将注释放到类之前的例子:
@Entity
public class Vehicle {
}
下面是一个更大的例子,演示了在类、成员变量、方法、参数以及局部变量之前添加注释。仅作演示之用,并没有什么特别的用意。
@Entity
public class Vehicle {
@Persistent
protected String vehicleName = null;
@Getter
public String getVehicleName() {
return this.vehicleName;
}
public void setVehicleName(@Optional vehicleName) {
this.vehicleName = vehicleName;
}
public List addVehicleNameToList(List names) {
@Optional
List localNames = names;
if(localNames == null) {
localNames = new ArrayList();
}
localNames.add(getVehicleName());
return localNames;
}
}
Java预置的编译注释
Java支持三个可以用来给编译相关的注释,它们是:
· @Deprecated
· @Override
· @SuppressWarings
下面将对它们此次做解释
@Deprecated
@Deprecated用来标记一个类、方法、成员变量已经被舍弃了。如果你的代码中使用舍弃(Deprecated)的类、方法或成员变量,那么编译器会给你一个警告。下面是一个例子:
@Deprecated
public class MyComponent {
}
当你使用@Deprecated表示舍弃时,你也可以在Java文档中对舍弃的原因加以说明。
@Override
@Override被用在方法前,用来说明覆盖了父类中的方法。假如一个方法被@Override修饰,但实际上它并没有覆盖任何方法,则编译器会提示一个错误。
@Override并不是必须的,即覆盖父类方法时,也可以不在子类方法前面添加@Override。但是还是推荐使用@Override,因为这样做是有好处的,至少可以较少一些不必要的错误。如覆盖方法的方法名不对,并没有实现覆盖;或者有人修改了父类中的方法名,导致的子类中的覆盖失效,如果有@Override,编译器就会自动提示错误,从而避免了错误。
@SuppressWarnings
使用@SuppressWarnings能够是编译器对指定的方法放弃提示警告。如方法中引用了已经被舍弃(@Deprecated修饰)的方法时。
创建你自己的注释
创建自己的注释是有可能的。注释被定义在它们自己的文件中,就像Java中的类或接口一样。下面是一个例子:
@interface MyAnnotation {
String value();
String name();
int age();
String[] newNames();
}
这个例子定义了一个包含四个元素的叫MyAnnotation的注释。
注意,每个元素的定义都很像接口中的方法定义。你可以使用原始数据类型定义元素的数据类型,你也可以使用数组定义元素的数据类型。但是不能使用复合对象(Complex Object定义元素的数据类型。
要使用上面自定义的注释,可以这样做:
@MyAnnotation(
value="123",
name="Jakob",
age=37,
newNames={"Jenkov", "Peterson"}
)
public class MyClass {
}
元素的默认值
你可以为一个元素指定默认值(有点像C++中的方法哈)。这样在注释初始化时那个元素就可以忽略了。如下定义了一个包含默认值的注释
@interface MyAnnotation {
String value() default "";
String name();
int age();
String[] newNames();
}
在调用时,可以忽略包含默认值的元素,这里指的是value元素,如:
@MyAnnotation(
name="Jakob",
age=37,
newNames={"Jenkov", "Peterson"}
)
public class MyClass {
}
@Retention
你可以指定你自定义的注释在运行时可用,通过反射检测。要实现这样的效果,你需要用@Retention修饰你自定义的注释,如下:
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
@Retention(RetentionPolicy.RUNTIME)
@interface MyAnnotation {
String value() default "";
}
这里的@Retention(RetentionPolicy.RUNTIME)会告诉编译器和JVM当前这个注释是可以在运行时通过反射机制访问的。
RetentionPolicy还包含了其他两个值:
RetentionPolicy.CLASS:意味着该注释需要被保存在.class文件中,但是在运行时是不可用的。这是retention默认的值。
RetentionPolicy.SOURCE:意味着该注释只在源代码中可用,而不是在.class文件,也不是在运行时。
@Target
你可以指定那些Java元素(类、方法等)可以使用你自定义的注释。可以在定义你的Annotaion添加@Target来实现。如下:
import java.lang.annotation.ElementType;
import java.lang.annotation.Target;
@Target({ElementType.METHOD})
public @interface MyAnnotation {
String value();
}
上面的代码限制了该注释只能用来注释方法(而不是类、成员变量之类的)
ElementType.ANNOTATION_TYPE
ElementType.CONSTRUCTOR
ElementType.FIELD
ElementType.LOCAL_VARIABLE
ElementType.METHOD
ElementType.PACKAGE
ElementType.PARAMETER
ElementType.TYPE
上面大多数数值都是可以见文知意的,其中ANNOTATION_TYPE表示只能用来注释注释类型(Annotation),就像@Target和@Retention一样。
@Inherited
@Inherited表明,一个子类实现了继承了父类中的注释,如下:
java.lang.annotation.Inherited
@Inherited
public @interface MyAnnotation {
}
@MyAnnotation
public class MySuperClass { ... }
public class MySubClass extends MySuperClass { ... }
在这个例子中,MySubClass继承了父类MySuperClass中的@MyAnnotation注释。
@Documented
@Documented用来表明你自定义的注释需要在JavaDoc中可见。如下:
java.lang.annotation.Documented
@Documented
public @interface MyAnnotation {
}
@MyAnnotation
public class MySuperClass { ... }
当你生成MySupperClass类的JavaDoc文档时,@MyAnnotation注释会出现在JavaDoc文档中。
这次不是"O啦~~~",而是哇偶~~~,终于结束了!!!
68 次点击
加入收藏