文章目录

  • 注解须知前言
  • @Target
  • @Retention
  • @Inherited
  • @Documented
  • @Repeatable

注解须知前言

Java注解使用是相当频繁,特别是在在框架源码使用,用到类的反射获取方法和属性,用的尤其多,而且即使是编写业务代码时候,也常有使用自定义注解来结合aop来实现减少代码的编写。

接下来我们就来解读一下Java注解。
Java中以前只有4个元注解,Java8后又新增了1个。

在讲解元注解概念之前,我们先建立元数据的概念。 元数据在英语中对应单词 metadata, metadata在wiki中的解释是:

Metadata is data [information] that provides information about other data

为其他数据提供信息的数据

这样元注解就好理解了,元注解 meta annotation用于注解 自定义注解 的注解。

接下来就看看Java中有哪些元注解,如下:

@Target 目标即作用范围
@Retention 保留
@Inherited 遗传,即注解是否可被继承
@Documented 文档,用javadoc命令生成API文档,会又相关信息


@Repeatable (java1.8 新增项)
当没有@Repeatable修饰的时候,注解在同一个位置,只能出现一次

接下来就进行注意讲解:

@Target

/** Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.* ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.*/package java.lang.annotation;/*** The constants of this enumerated type provide a simple classification of the* syntactic locations where annotations may appear in a Java program. These* constants are used in {@link Target java.lang.annotation.Target}* meta-annotations to specify where it is legal to write annotations of a* given type.** <p>The syntactic locations where annotations may appear are split into* <em>declaration contexts</em> , where annotations apply to declarations, and* <em>type contexts</em> , where annotations apply to types used in* declarations and expressions.** <p>The constants {@link #ANNOTATION_TYPE} , {@link #CONSTRUCTOR} , {@link* #FIELD} , {@link #LOCAL_VARIABLE} , {@link #METHOD} , {@link #PACKAGE} ,* {@link #PARAMETER} , {@link #TYPE} , and {@link #TYPE_PARAMETER} correspond* to the declaration contexts in JLS 9.6.4.1.** <p>For example, an annotation whose type is meta-annotated with* {@code @Target(ElementType.FIELD)} may only be written as a modifier for a* field declaration.** <p>The constant {@link #TYPE_USE} corresponds to the 15 type contexts in JLS* 4.11, as well as to two declaration contexts: type declarations (including* annotation type declarations) and type parameter declarations.** <p>For example, an annotation whose type is meta-annotated with* {@code @Target(ElementType.TYPE_USE)} may be written on the type of a field* (or within the type of the field, if it is a nested, parameterized, or array* type), and may also appear as a modifier for, say, a class declaration.** <p>The {@code TYPE_USE} constant includes type declarations and type* parameter declarations as a convenience for designers of type checkers which* give semantics to annotation types. For example, if the annotation type* {@code NonNull} is meta-annotated with* {@code @Target(ElementType.TYPE_USE)}, then {@code @NonNull}* {@code class C {...}} could be treated by a type checker as indicating that* all variables of class {@code C} are non-null, while still allowing* variables of other classes to be non-null or not non-null based on whether* {@code @NonNull} appears at the variable's declaration.** @author  Joshua Bloch* @since 1.5* @jls 9.6.4.1 @Target* @jls 4.1 The Kinds of Types and Values*/
public enum ElementType {/** Class, interface (including annotation type), or enum declaration */TYPE,/** Field declaration (includes enum constants) */FIELD,/** Method declaration */METHOD,/** Formal parameter declaration */PARAMETER,/** Constructor declaration */CONSTRUCTOR,/** Local variable declaration */LOCAL_VARIABLE,/** Annotation type declaration */ANNOTATION_TYPE,/** Package declaration */PACKAGE,/*** Type parameter declaration** @since 1.8*/TYPE_PARAMETER,/*** Use of a type** @since 1.8*/TYPE_USE
}

@Target 表示这个注解能放在什么位置上,是只能放在类上?还是即可以放在方法上,又可以放在属性上。从源码中可见,目标注解的值是一个数组,举个例子

@Target({METHOD,TYPE}),表示他可以用在方法和类型上(类和接口),但是不能放在属性等其他位置。

可以选择的位置列表如下:

值得注意的是,在Java8ElementType 新增两个枚举成员TYPE_PARAMETERTYPE_USE ,在Java8前注解只能标注在一个声明(如字段、类、方法)上,Java8后,新增的TYPE_PARAMETER可以用于标注类型参数,而TYPE_USE则可以用于标注任意类型(不包括class)。如下所示

ElementType.TYPE:能修饰类、接口或枚举类型
ElementType.FIELD:能修饰成员变量
ElementType.METHOD:能修饰方法
ElementType.PARAMETER:能修饰参数
ElementType.CONSTRUCTOR:能修饰构造器
ElementType.LOCAL_VARIABLE:能修饰局部变量
ElementType.ANNOTATION_TYPE:能修饰注解
ElementType.PACKAGE:能修饰包

@Retention


@Retention 表示生命周期

RetentionPolicy.SOURCE: 注解只在源代码中存在,编译成class之后,就没了。@Override 就是这种注解。
RetentionPolicy.CLASS: 注解在java文件编程成.class文件后,依然存在,但是运行起来后就没了。@Retention的默认值,即当没有显式指定@Retention的时候,就会是这种类型。
RetentionPolicy.RUNTIME: 注解在运行起来之后依然存在,程序可以通过反射获取这些信息

@Inherited


翻译注释即:

指示注释类型是自动继承的。如果注释类型声明中存在继承的元注释,并且用户在类声明中查询该注释类型,并且该类声明没有该类型的注释,则将自动查询该类的超类以获取注释类型。重复此过程,直到找到该类型的注释,或到达类层次结构(对象)的顶部为止。如果没有超类对此类型进行注释,则查询将指示所讨论的类没有此类注释。请注意,如果带注释的类型用于注释除类之外的任何内容,则此元注释类型无效。还要注意,此元注释仅使注释从超类继承;已实现的接口上的注释无效。

@Inherited 表示该注解具有继承性。
即如果一个使用了@Inherited 修饰的annotation 类型被用于一个class,则这个annotation 将被用于该class 的子类。

@Documented

@Documented 如图所示, 在用javadoc命令生成API文档后,文档里会出现该注解说明

@Repeatable


元注解@Repeatable是JDK1.8新加入的,它表示在同一个位置重复相同的注解。在没有该注解前,一般是无法在同一个类型上使用相同的注解的。

//Java8前无法这样使用
@FilterPath("/update")
@FilterPath("/add")
public class A {}

Java8前如果是想实现类似的功能,我们需要在定义@FilterPath注解时定义一个数组元素接收多个值如下:

@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
public @interface FilterPath {String [] value();
}//使用
@FilterPath({"/update","/add"})
public class A { }
@Target({ElementType.TYPE,ElementType.FIELD,ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Repeatable(FilterPaths.class)//参数指明接收的注解class
public @interface FilterPath {String  value();
}@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@interface FilterPaths {FilterPath[] value();
}//使用案例
@FilterPath("/update")
@FilterPath("/add")
@FilterPath("/delete")
class AA{ }

Java注解解读-ElementType详解相关推荐

  1. java注解和反射详解

    注解 什么是注解 Annotation是从JDK1.5开始引入的新技术 Annotation的作用: 不是程序本身,可以对程序做出解释 可以被其他程序读取 Annotation的格式: ​ 注解是以& ...

  2. Java注解处理器使用详解

    文章转自:http://www.race604.com/annotation-processing/ 在这篇文章中,我将阐述怎样写一个注解处理器(Annotation Processor).在这篇教程 ...

  3. Java单元测试之JUnit4详解

    2019独角兽企业重金招聘Python工程师标准>>> Java单元测试之JUnit4详解 与JUnit3不同,JUnit4通过注解的方式来识别测试方法.目前支持的主要注解有: @B ...

  4. Java编程配置思路详解

    Java编程配置思路详解 SpringBoot虽然提供了很多优秀的starter帮助我们快速开发,可实际生产环境的特殊性,我们依然需要对默认整合配置做自定义操作,提高程序的可控性,虽然你配的不一定比官 ...

  5. Java基础学习总结(24)——Java单元测试之JUnit4详解

    Java单元测试之JUnit4详解 与JUnit3不同,JUnit4通过注解的方式来识别测试方法.目前支持的主要注解有: @BeforeClass 全局只会执行一次,而且是第一个运行 @Before  ...

  6. java 8 新功能详解_Java 8和Java 14之间的新功能

    java 8 新功能详解 从版本9开始,Java每6个月就有一次新功能,因此很难跟踪这些新更改. 互联网上的大多数信息都描述了最近2个Java版本之间的变化. 但是,如果您的情况与我相似,则说明您使用 ...

  7. Java基准测试工具JMH详解

    Java基准测试工具JMH详解 1.JMH概述 1.1 JMH简介 1.2 JMH与JMeter区别 1.3 JMH注解说明 2.JMH验证 2.1 创建项目 2.2 引入依赖 2.3 启动异常解决 ...

  8. Java线程池ThreadPool详解

    Java线程池ThreadPool详解 1. 线程池概述 1.1 线程池简介 1.2 线程池特点 1.3 线程池解决问题 2. 线程池原理分析 2.1 线程池总体设计 2.6 线程池流转状态 2.2 ...

  9. java -jar 和 -cp详解

    java -jar 和 -cp详解 命令行执行程序 假如我们有一个程序,把它打包成Test.jar,如何运行才能成功输出Hello World package com.test; public cla ...

最新文章

  1. 阿里三面,P9面试官是如何360°无死角考察候选人的?
  2. POJ 1789 Truck History
  3. [翻译]IE8下VML的变化
  4. Scrum失败/成功案例分析
  5. 动态规划算法-02矿工挖矿问题
  6. SE81 - Application hierarchy CSS component tree
  7. Android Scrollview嵌套RecyclerView导致滑动卡顿问题解决(屡试不爽)
  8. ASP.NET MVC 入门2、项目的目录结构与核心的DLL
  9. 提升沟通效率52%  阿里政务钉钉助力政府数字化转型
  10. 我是如何一步一步成为高级前端开发工程师的
  11. php之数据类型自动转换
  12. Qt5中this application has requested the runtime to terminate it in an unusual way 无法运行问题的解决
  13. 最全电缆直径和电缆流过电流计算以及对照表
  14. 券商股票程序化交易接口(转)
  15. 用Prolog解决爱因斯坦斑马问题
  16. 六爻:起卦、装卦、断卦
  17. writev遇到非阻塞IO
  18. cs231n计算机视觉课程笔记
  19. java开发可视化界面_java 可视化界面编程
  20. JavaSwing_3.5: JLayeredPane(层级面板)

热门文章

  1. 1041-不含重复字符的最长子字符串
  2. EQT从Micro Focus手中买下了SUSE,SUSE将何去何从?
  3. yshop前后端分离商城系统v3.2拼团砍价秒杀+商品积分兑换+商城装修
  4. CocosCreator物理小游戏实战-别离开碗(一)
  5. 新闻!中韧国际教育翼次元学院的少儿有艺翼行动与针对少儿的“艺术饭+”行动在京开幕
  6. js/javascript 操作数组【全】(含常用的操作数组的lodash)
  7. 查询SQL中连续编号中间的断号
  8. Jenkins 构建job无法停止问题
  9. SpringBoot整合mybatis时报Invalid bound statement (not found)错误的可能原因
  10. 图像化转向名词解释_视觉文化