注解的主要用途是用于替代配置文件;注解本身是有参数的;注解主要是给反射技术用的。
//自定义一个注解(在idea中无annotation关键字,只是一个接口)
//@Retention为注解中存在的“生命周期”范围
//RetentionPolicy.SOURCE:只存在于源代码级别
//RetentionPolicy.CLASS:存在于源代码和class文件中
//RetentionPolicy.RUNTIME:存在于源代码、class文件和运行时(JVM运行代码时可以使用)
@Retention(RetentionPolicy.RUNTIME)
//@Target指定当前注解能够出现在那些位置
//ElementType.TYPE:类(接口、枚举、注解)的前面
//ElementType.METHOD:方法前
//ElementType.FIELD:属性前
//ElementType.PARAMETER:参数前
@Target({ElementType.FIELD, ElementType.METHOD})
public @interface MyAnnotation {
String value() default "这是默认值";
String name() default "张三";
String pass() default "123456";
int age() default 25;
}
//建立一个Bean类
public class Student {
private String stuName;
private String stuPass;
private String clazz;
private Integer age;
@Override
public String toString() {
return "Student{" +
"stuName='" + stuName + '\'' +
", stuPass='" + stuPass + '\'' +
", clazz='" + clazz + '\'' +
", age=" + age +
'}';
}
//只是为了演示做什么,位置不必放在这里
@MyAnnotation(value = "软工201901班",name = "张三") //没有写属性自动填写默认值
public void showStudent(){
System.out.println("学生名叫:" + stuName + "密码为:" + stuPass + "年龄为" + age + "班级为:" + clazz);
}
public String getStuName() {
return stuName;
}
public void setStuName(String stuName) {
this.stuName = stuName;
}
public String getStuPass() {
return stuPass;
}
public void setStuPass(String stuPass) {
this.stuPass = stuPass;
}
public String getClazz() {
return clazz;
}
public void setClazz(String clazz) {
this.clazz = clazz;
}
public Integer getAge() {
return age;
}
public void setAge(Integer age) {
this.age = age;
}
}
//测试运行
public static void main(String[] args) {
//使用反射技术,创建一个学生对象
//1.获取学生类的“反射类型”
Class<Student> stuClass = Student.class;
//2.通过类的无参构造方法,创建对象
Student stu = null;
try {
stu = stuClass.newInstance();
} catch (InstantiationException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
}
//3.准备4个临时变量,存放从注解中获取的四个值
String name = null;
String pass = null;
String clazz = null;
Integer age = null;
//4.获取学生类的所有方法形成的数组,准备遍历他们,判断哪个方法前使用了我们自定义的注解
Method[] methods = stuClass.getDeclaredMethods();
for(Method method: methods){
//尝试获取当前方法前的自定义注解“@MyAnnotation”
MyAnnotation myAnno = method.getAnnotation(MyAnnotation.class);
if(myAnno != null){
//注解不为空,说明当前方法前,使用了自定义注解“@MyAnnotation”
//接下来,我们开始从注解中获取填入的参数值
name = myAnno.name();
pass = myAnno.pass();
age = myAnno.age();
clazz = myAnno.value();
}
}
//5.给Student学生对象,4个属性赋值
stu.setStuName(name);
stu.setStuPass(pass);
stu.setAge(age);
stu.setClazz(clazz);
System.out.println(stu);
}
运行结果
Student{stuName='张三', stuPass='123456', clazz='软工201901班', age=25}