目录
- 一、Java自定义注解详解
- 1.定义注解:
- 2.元注解介绍
- @Target详细介绍
- @Relation详细介绍
- @Documented介绍
- @Inherited介绍
- 3.注解可用的类型
- 4.默认值限制
- 5.创建一个简单的自定义注解
- 二、读取注解上的信息
一、Java自定义注解详解
1.定义注解:
注解的定义很像接口的定义。事实上与其他java接口一样,注解也会被编译成class文件。定义注解时需要一些元注解。
2.元注解介绍
@Target详细介绍
值 | 描述 |
ElementType.TYPE | 接口、类、枚举、注解 |
ElementType.FIELD | 字段、枚举的常量 |
ElementType.METHOD | 方法 |
ElementType.PARAMETER | 方法参数 |
ElementType.CONSTRUCTOR | 构造函数 |
ElementType.LOCAL_VARIABLE | 局部变量 |
ElementType.ANNOTATION_TYPE | 注解 |
ElementType.PACKAGE | 包 |
@Relation详细介绍
值 | 描述 |
RetentionPolicy.SOURCE | 注解将被编译器丢弃,此处是源码阶段也就是javac编译时 |
RetentionPolicy.CLASS | 注解在class中可用,但会被vm丢弃 |
RetentionPolicy.RUNTIME | vm运行期间也会保留注解,可以使用反射机制读取注解的信息 |
@Documented介绍
将此注解包含在javadoc中
@Inherited介绍
允许子类继承父类中的注解,千万不要误解是注解的嵌套,是Class类继承的时候,是否拥有父类的注解
3.注解可用的类型
- 所有基本类型(int、float、double,boolean)
- String
- Class
- enum
- Annotaion
- 以上类型的数组
注解可以嵌套注解
4.默认值限制
元素必须具有默认值,默认值不能是null
注解不支持继承,不像类一样可以通过extends继承
5.创建一个简单的自定义注解
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
public @interface CustomAnnotation {
}二、读取注解上的信息
通过反射机制去获取注解上的信息
- 创建各种类型的注解
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
public @interface AnnotationForClass {
String value();
}
@Target(ElementType.CONSTRUCTOR)
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
public @interface AnnotationForConstructor {
String value();
}
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
public @interface AnnotationForField {
String value();
}
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
public @interface AnnotationForMethod {
String value();
}
@Target(ElementType.PARAMETER)
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
public @interface AnnotationForParam {
String value();
}- 带有各种注解的测试类
@AnnotationForClass(value = "AnnotationForClassValue")
public class Test {
@AnnotationForField(value = "AnnotationForFieldValue")
private String name;
@AnnotationForMethod(value = "AnnotationForMethodValue")
public String getName() {
return ;
}
public void setName(@AnnotationForParam(value = "AnnotationForParamValue") String name) {
= name;
}
@AnnotationForConstructor(value = "AnnotationForConstructorValue")
public Test() {
}
}- 获取注解以及注解上的信息
public class Main {
// getDeclaredAnnotations 获取所有的注解
// getDeclaredAnnotation 获取指定的注解
public static void main(String[] args) throws NoSuchMethodException, NoSuchFieldException {
Class<Test> testClazz = Test.class;
// 获取(类、接口、枚举、注解)上注解的
AnnotationForClass annotationForClass = testClazz.getDeclaredAnnotation(AnnotationForClass.class);
System.out.println("类上的注解的值\t" + annotationForClass.value());
// 获取类中构造器的注解
Constructor<Test> constructor = testClazz.getConstructor();
AnnotationForConstructor annotationForConstructor = constructor.getDeclaredAnnotation(AnnotationForConstructor.class);
System.out.println("类中构造器的注解的值\t" + annotationForConstructor.value());
// 获取类中字段的注解
Field nameField = testClazz.getDeclaredField("name");
AnnotationForField annotationForField = nameField.getDeclaredAnnotation(AnnotationForField.class);
System.out.println("类中字段的注解的值\t" + annotationForField.value());
// 获取类中方法的注解
Method getNameMethod = testClazz.getDeclaredMethod("getName");
AnnotationForMethod annotationForMethod = getNameMethod.getDeclaredAnnotation(AnnotationForMethod.class);
System.out.println("类中方法的注解的值\t" + annotationForMethod.value());
// 获取方法上参数的注解
Method setNameMethod = testClazz.getDeclaredMethod("setName", String.class);
AnnotationForParam annotationForParam = setNameMethod.getDeclaredAnnotation(AnnotationForParam.class);
System.out.println("类中方法的参数的注解的值\t" + annotationForParam.value());
}
}- 运行结果
类上的注解的值 AnnotationForClassValue
类中构造器的注解的值 AnnotationForConstructorValue
类中字段的注解的值 AnnotationForFieldValue
类中方法的注解的值 AnnotationForMethodValue
类中方法的参数的注解的值 AnnotationForParamValue
















