java-注解
使用注解
注解(Annotation)是放在Java源码的类、方法、字段、参数前的一种标签。
注解本身对代码逻辑没有任何影响,如何使用注解由工具决定。
编译器可以使用的注解:
-
@Override让编译器检查该方法是否正确实现了覆写 -
@Deprecated告诉编译器,该方法被标记为“作废”,在其他地方引用将会出现警告 -
@SuppressWarnings告诉编译器,在这个方法内部如果出现警告,编译器会忽略这些编译警告。public class Hello {
@Override
public String toString() {
return "Hello";
}
@Deprecated
public void hello(String name) {
System.out.println("name");
}
@SuppressWarnings("unused")
public void hello() {
int n; //local variable n is not used
}}
注解可以定义配置参数和默认值。
-
配置参数由注解类型定义
-
配置参数可以包括:
-
所有的基本类型
-
String
-
枚举
-
数组
-
-
配置参数必须是常量
public class Hello {
int n=100;
@Test(timeout=100)
public void test() {
System.out.println("Test");
}
} -
缺少某个配置参数将使用默认值
-
如果只写常量相当于省略了value参数
-
如果只写注解相当于全部使用默认
public class Hello {
@Check(min=0,max=100,value=50)
public int n;@Check(value=99)
public int p;@Check(99) ///@Check(value=99)
public int x;@Check
public int y;
}
定义注解
使用@interface定义注解(Annotation)
-
注解的参数类似无参方法
-
可以设定一个默认值(推荐)
-
把最常用的参数值命名为value(推荐)
public @interface Report {
int type() default 0;
String level() default "info";
String value() default "";
}
使用元注解定义注解:
-
@Target定义Annotation 可以被应用于源码的那些位置:-
类和接口 :ElementType.TYPE
-
字段:ElementType.FIELD
-
方法:ElementType.METHOD
-
构造方法:ElementType.CONSTRUCTOR
-
方法参数:ElementType.PARAMETER
@Target(ElementType.METHOD)
public @interface Report {
int type() default 0;
String level() default "info";
String value() default "";
}
-
-
@Retention定义Annotation的生命周期-
仅编译期:RetentionPolicy.SOURCE
-
仅class文件:RetentionPolicy.CLASS
-
运行期:RetentionPolicy.RUNTIME
-
如果
@Retention不存在,则该Annotation默认为CLASS -
通常自定义的Annotation都是RUNTIME
@Retention(RetentionPolicy.RUNTIME)
public @interface Report {
int type() default 0;
String level() default "info";
String value() default "";
}
-
-
@Repeatable定义 Annotation是否可重复- JDK > 1.8
-
@Inherited定义子类是否可以继承父类的Annotation- 仅针对
@Target为Type类型的Annotation - 仅针对class的继承
- 对interface的继承无效
- 仅针对
定义Annotation的步骤:
-
用
@interface定义注解 -
用元注解(meta annotation)配置注解
Target:必须设置
Retention:一般设置为RUNTIME
通常不必写@Inherited, @Repeatable等等 -
定义注解参数和默认值
处理注解
使用反射API读取Annotation:
-
Class.isAnnotationPresent(Class)
-
Field.isAnnotationPresent(Class)
-
Method.isAnnotationPresent(Class)
-
Constructor.isAnnotationPresent(Class)
Class cls = Person.class;
//判断@Report是否存在
cls.isAnnotationPresent(Report.class); -
Class.getAnnotation(Class)
-
Field.getAnnotation(Class)
-
Method.getAnnotation(Class)
-
Constructor.getAnnotation(Class)
Class cls = Person.class;
cls.isAnnotationPresent(Report.class);
Report report = cls.getAnnotation(Report.class);
//如果不存在返回null
int type = report.type();
String level = report.level(); -
getParameterAnnotations() //返回一个二位数组
可以通过工具处理注解来实现相应的功能:
-
对JavaBean的属性值按规则进行检查
-
JUnit会自动运行
@Test标记的测试方法
浙公网安备 33010602011771号