Java自定义注解学习
Posted 清风拂来
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Java自定义注解学习相关的知识,希望对你有一定的参考价值。
1.定义一个枚举类,后面自定义注解时使用
1 package cn.tx.annotation.enums; 2 /** 3 * 定义枚举类型 4 * @author Administrator 5 * 6 */ 7 public enum HttpMethod { 8 9 GET,POST,PUT,INPUT,DELETE; 10 }
2. 自定义一个注解 AnnoTest
1 package cn.tx.annotation; 2 3 import java.lang.annotation.Documented; 4 import java.lang.annotation.ElementType; 5 import java.lang.annotation.Retention; 6 import java.lang.annotation.RetentionPolicy; 7 import java.lang.annotation.Target; 8 9 import cn.tx.annotation.enums.HttpMethod; 10 11 /** 12 * 1.自定义注解,自动实现了java.lang.Annotation接口 13 * @author Administrator 14 * 2.注解内部可以定义值,这里的值既不是属性,也不是方法 15 * 3.语法:数据类型 值的名字(); 16 * 4.注解的意义:当非标识性注解(内部有值的注解)标注在方法上时,当方法被反射调用时,注解才有意义 17 * 5.@Retention 注解 18 * @Retention(RetentionPolicy.RUNTIME) 19 * @Target(ElementType.ANNOTATION_TYPE) public @interface Retention { 20 * RetentionPolicy value(); } 21 * RetentionPolicy:注解的策略 22 * RetentionPolicy.CLASS 表示这个注解能被编译到class文件里,但是运行时不参与运行 23 * 6.@Target注解——指示注解类型所适用的程序元素的种类 24 * @Documented 25 @Retention(RetentionPolicy.RUNTIME) 26 @Target(ElementType.ANNOTATION_TYPE) 27 public @interface Target { 28 ElementType[] value(); 29 ElementType是一个枚举类型 30 } 31 * 7. @Target @Retention 只能用在注解的定义上面 32 * 8.@Documented 指明该注解将被包含在javadoc中 33 */ 34 35 //ElementType.METHOD,表示AnnoTest只能放在方法上面,不能放在类,属性等其他上面 36 @Target(value = { ElementType.METHOD,ElementType.TYPE }) 37 @Retention(value = RetentionPolicy.RUNTIME) 38 public @interface AnnoTest { 39 40 String value();//这里定义了值,在使用注解的地方,就得加上这个值 41 42 // Class[]/*String[]*/ location(); 43 44 // HttpMethod method(); 45 46 } 47 48 49 // enum ElementType { 50 // /**类,接口,枚举声明 Class, interface (including annotation type), or enum declaration */ 51 // TYPE, 52 // /**字段声明,包括枚举常量 Field declaration (includes enum constants) */ 53 // FIELD, 54 // /**方法声明 Method declaration */ 55 // METHOD, 56 // /** Parameter declaration */ 57 // PARAMETER, 58 // /** 构造方法声明 Constructor declaration */ 59 // CONSTRUCTOR, 60 // /**局部变量声明 Local variable declaration */ 61 // LOCAL_VARIABLE, 62 // /**注解类型声明 Annotation type declaration */ 63 // ANNOTATION_TYPE, 64 // /**包声明 Package declaration */ 65 // PACKAGE 66 //}
3. 定义一个Claculate类,对方法使用自定义注解(前提是AnnoTest 注解 设置的@Target(value = { ElementType.METHOD,ElementType.TYPE }) ,也就是该注解能被使用在方法上面。)
1 package cn.tx.annotation.test; 2 3 import java.lang.annotation.ElementType; 4 import java.lang.annotation.Target; 5 6 import cn.tx.annotation.AnnoTest; 7 8 public class Caculate { 9 // @AnnoTest(value = "sss") 10 //AnnoTest注解中定义了@Target(value = { ElementType.METHOD,ElementType.TYPE }) 11 //如果在属性a上面加@AnnoTest注解,会报:The annotation @AnnoTest is disallowed for this location 12 private int a; 13 14 @AnnoTest(value = "相加的结果是:") 15 public int add(int a,int b){ 16 return a+b; 17 } 18 19 }
4. junit测试类:
1 package cn.tx.annotation.test; 2 3 import java.lang.annotation.Documented; 4 import java.lang.annotation.ElementType; 5 import java.lang.annotation.Retention; 6 import java.lang.annotation.RetentionPolicy; 7 import java.lang.annotation.Target; 8 import java.lang.reflect.Method; 9 import java.util.ArrayList; 10 import java.util.List; 11 12 import cn.tx.annotation.AnnoTest; 13 import cn.tx.annotation.enums.HttpMethod; 14 15 /** 16 * 常用的表标识性注解:@Test @Override @SuppressWarnings 17 * 18 * @author Administrator 19 * 20 */ 21 public class Test { 22 23 @org.junit.Test 24 public void test() { 25 26 } 27 28 // @AnnoTest(value = "tst") 29 @Deprecated 30 // 过时,不建议使用的注解 31 public void method() { 32 33 } 34 35 /** 36 * @SuppressWarnings压制警告的注解 unchecked 不检查操作时的警告 rawtypes 37 * 原始类型,也就是不使用泛型,在定义的时候压制泛型的警告 38 */ 39 @SuppressWarnings( { "unchecked", "rawtypes" }) 40 public void method1() { 41 @SuppressWarnings("unused") 42 List list = new ArrayList();// 不写泛型类型时,会出现黄色波浪线警告! 43 list.add("lisi"); 44 } 45 46 @org.junit.Test 47 // @AnnoTest(value = "test", location = { String.class }, method = HttpMethod.GET) 48 // 非标识性注解的意义在于方法被反射调用时 49 public void method3() { 50 51 } 52 53 @org.junit.Test 54 public void testEnum() { 55 System.out.println(HttpMethod.GET); //执行该方法,控制台打印GET 56 } 57 58 @org.junit.Test 59 public void testAdd(){ 60 new Caculate().add(3, 5); //正常调用,add方法上面的注解不会起作用 61 } 62 63 @org.junit.Test 64 public void testAdd1(){ 65 //获取Caculate类的Class对象,进而获得一个实例,然后获取声明的方法及方法上的注解 66 Class<?> clazz = Caculate.class; 67 try { 68 Object obj = clazz.newInstance(); 69 //getFields()只能获取public的字段,包括父类的。getDeclaredFields()只能获取自己声明的各种字段,包括public,protected,private。 70 Method method = clazz.getDeclaredMethod("add", int.class,int.class); 71 //判断一个方法上面是否存在某个注解 72 boolean isPres = method.isAnnotationPresent(AnnoTest.class); 73 if(isPres){ 74 //根据一个类获取注解 ,即获得@AnnoTest 75 AnnoTest annotation = method.getAnnotation(AnnoTest.class); 76 //获得注解上的值 77 String value = annotation.value(); // 78 //反射的方式调用add()方法 79 Object result = method.invoke(obj, 2,3); 80 System.out.println(value+result); //控制台输出结果为: 相加的结果是:5 81 //如果注解上的@Retention(value = RetentionPolicy.SOURCE),运行时时不会有结果的 82 } 83 84 } catch (Exception e) { 85 e.printStackTrace(); 86 } 87 88 } 89 90 }
以上是关于Java自定义注解学习的主要内容,如果未能解决你的问题,请参考以下文章