Java注解(二)

前面了解了注解的基本内容,这次来看一下自定义注解。

自定义注解其实很简单,直接上代码:

import java.lang.annotation.Documented;
import java.lang.annotation.Inherited;
import java.lang.annotation.Retention;
import java.lang.annotation.Target;
import java.lang.annotation.ElementType;
import java.lang.annotation.RetentionPolicy;

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
/*

  • 定义注解 Test
  • 注解中含有两个元素 id 和 description
  • description 元素 有默认值 "hello anntation"
    */
    public @interface Test {
    public int id();
    public String description() default "hello annotation";
    }

 根据上一篇对元注解的解释,我们知道:

  1. 这个注解可以用于方法
  2. JVM 运行期间该注解都有效
  3. 该注解包含在 javadoc 中
  4. 该注解允许子类继承

 下面看下通过注解我们能取到什么

public class TestMain {  
    /* 
     * 被注解的三个方法 
     */  
    @Test(id = 1, description = "hello methodA")  
    public void methodA(){}  
@Test(id </span>= 2<span style="color: rgba(0, 0, 0, 1)">)  
</span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> methodB() {  
}  

@Test(id </span>= 3, description = "last method"<span style="color: rgba(0, 0, 0, 1)">)  
</span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> methodC() {  
}  

</span><span style="color: rgba(0, 128, 0, 1)">/*</span><span style="color: rgba(0, 128, 0, 1)"> 
 * 解析注解,将类被注解方法 的信息打印出来 
 </span><span style="color: rgba(0, 128, 0, 1)">*/</span>  
<span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">static</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> main(String[] args) {  
    Method[] methods </span>= TestMain.<span style="color: rgba(0, 0, 255, 1)">class</span><span style="color: rgba(0, 0, 0, 1)">.getDeclaredMethods();  
    </span><span style="color: rgba(0, 0, 255, 1)">for</span><span style="color: rgba(0, 0, 0, 1)"> (Method method : methods) {  
        </span><span style="color: rgba(0, 128, 0, 1)">/*</span><span style="color: rgba(0, 128, 0, 1)"> 
         * 判断方法中是否有指定注解类型的注解 
         </span><span style="color: rgba(0, 128, 0, 1)">*/</span>  
        <span style="color: rgba(0, 0, 255, 1)">boolean</span> hasAnnotation = method.isAnnotationPresent(Test.<span style="color: rgba(0, 0, 255, 1)">class</span><span style="color: rgba(0, 0, 0, 1)">);  
        </span><span style="color: rgba(0, 0, 255, 1)">if</span><span style="color: rgba(0, 0, 0, 1)"> (hasAnnotation) {  
            </span><span style="color: rgba(0, 128, 0, 1)">/*</span><span style="color: rgba(0, 128, 0, 1)"> 
             * 根据注解类型返回方法的指定类型注解 
             </span><span style="color: rgba(0, 128, 0, 1)">*/</span><span style="color: rgba(0, 0, 0, 1)">  
            Test annotation </span>= method.getAnnotation(Test.<span style="color: rgba(0, 0, 255, 1)">class</span><span style="color: rgba(0, 0, 0, 1)">);  
            System.out.println(</span>"Test( method = " + method.getName() + " , id = " +<span style="color: rgba(0, 0, 0, 1)"> annotation.id() 
                    </span>+ " , description = " + annotation.description() + " )"<span style="color: rgba(0, 0, 0, 1)">);
        }  
    }  
}  

}

 上面的 Demo 打印的结果如下:

Test( method = methodA , id = 1 , description = hello methodA )
Test( method = methodB , id = 2 , description = hello annotation )
Test( method = methodC , id = 3 , description = last method )

 上例其实也说明了,我们一般通过反射来取RUNTIME 保留策略的注解信息。