一、自定义注解元注解的讲解
package com.test.annotation;
import static java.lang.annotation.ElementType.CONSTRUCTOR;
import static java.lang.annotation.ElementType.FIELD;
import static java.lang.annotation.ElementType.LOCAL_VARIABLE;
import static java.lang.annotation.ElementType.METHOD;
import static java.lang.annotation.ElementType.PARAMETER;
import static java.lang.annotation.ElementType.TYPE;
import java.lang.annotation.Documented;
import java.lang.annotation.Inherited;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* 我的自定义注解
* @author dgw
* java 5.0定义了4个标准的元注解,@Target,@Retention,@Documented,@Inherited
*
* @Target:定义了注解的使用范围
* ElementType:ANNOTATION_TYPE 声明注解类型
* ElementType:CONSTRUCTOR 声明构造函数
* ElementType:FIELD 声明字段(包括枚举常量)
* ElementType:LOCAL_VARIABLE 声明局部变量
* ElementType:METHOD 声明方法
* ElementType:PACKAGE 声明包
* ElementType:PARAMETER 声明参数
* ElementType:TYPE 声明类
*
* @Retention:描述注解的声明周期
* RetentionPolicy:CLASS 在编译文件中保留,但不会加载到VM中(默认行为)
* RetentionPolicy:SOURCE 在源文件中有效
* RetentionPolicy:RUNTIME 在运行时有效,一般自己定义这个用得比较多,选了这个上面两个默认有效
*
* @Documented:标记性注解,将此注解包含在 javadoc 中 ,它代表着此注解会被javadoc工具提取成文档。
* 在doc文档中的内容会因为此注解的信息内容不同而不同。
*
* @Inherited:继承注解,可以吧这个注解标注在自己的注解类上,当使用时,父类使用了此注解,子类也会继承此注解。
*
*/
@Target({TYPE, FIELD, METHOD, PARAMETER, CONSTRUCTOR, LOCAL_VARIABLE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
public @interface MyAnnotation {
/**
* 当注解只有一个参数是我们通常使用value,
* default注解参数的默认值,一般为空字符串"",0或者-1
*/
String[] value() default {};
}
二、类注解、属性注解和方法注解的讲解
1、先来定义一个类注解,模拟orm框架中的@Table注解
package com.test.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Inherited;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target(ElementType.TYPE)//次注解用于类
@Retention(RetentionPolicy.RUNTIME)//次注解在运行时有效
@Documented
@Inherited
public @interface MyTable {
String table();
}
2、定义一个属性注解
package com.test.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Inherited;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target(ElementType.FIELD)//次注解用于字段
@Retention(RetentionPolicy.RUNTIME)//次注解在运行时有效
@Documented
@Inherited
public @interface MyField {
String field();
String type();
int length();
}
3、定义一个方法注解
package com.test.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Inherited;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target(ElementType.METHOD)//次注解用于方法
@Retention(RetentionPolicy.RUNTIME)//次注解在运行时有效
@Documented
@Inherited
public @interface MyMothed {
String value() default "赵敏";
}
4、定义一个类,在构造函数中用反射为对象赋值
package com.test.annotation;
import java.lang.reflect.Method;
@MyTable(table="t_person_b")
public class Person {
public Person(){
Class clazz=this.getClass();
Method[] methods = clazz.getMethods();
for(Method method:methods){
if(method.getName().equals("getName")){
MyMothed annotation = method.getAnnotation(MyMothed.class);
this.setName(annotation.value());
}
}
}
@MyField(field="id",type="int",length=10)
private Integer id;
@MyField(field="name",type="varchar",length=100)
private String name;
@MyField(field="age",type="int",length=10)
private Integer age;
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
@MyMothed(value="敏敏特穆尔")
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Integer getAge() {
return age;
}
public void setAge(Integer age) {
this.age = age;
}
}
5,测试在getName方法上有注解@MyMothed(value="敏敏特穆尔")时,输出的实敏敏特穆尔,没有value值时输出的时赵敏
package com.test.annotation;
/**
* 用放射机制读取注解,测试自定义注解
* @author dgw
*
*/
public class TestMyAnnotation {
public static void main(String[] args) {
Person person = new Person();
System.out.println(person.getName());//敏敏特穆尔或赵敏
}
}