注解之注解的基本概念

一.什么是注解

        annotation是注解的意思 ,注解可以理解为标记,用来标记一些辅助信息。 

       其实呢,Java中有一类接口 本身不用被实现,只是作为一个标记用的存在。

   标记的目的显然是为了进行  区别,识别,分类,这样做的目的 就明显了,分类之后可以制定统一的规则来进行处理。处理的依据就是注解里面含有的信息.

   那么注解本身就是一个标记,可以用于分类,从而使用注解可以  获取一个 类的集合或者是一个方法的集合..

  从而为我们下一步的处理提供一个输入集合,可以让我们以一个高度统一的动作来处理一些  同一个标记的 对象

 

   领悟其中的精髓:  标记,分类,储存辅助信息.

    有了这个标记,我们可以使用反射来分析类,然后进行归类,(aop 的切点不也是为了进行归类吗),

    辅助的信息其实就是可以放到配置文件中的那些配置信息,这些东西的灵活配置增加了灵活度,因此注解里面可以放置一些固定的信息

   有了这些 作用,那么就可以依据注解里面的配置信息 对注解修饰的  东西 (类,对象,字段,方法)  进行一些处理。

  比如  : 校验 ,我们可以在VO的字段上加上注解来存储校验的规则信息,当然这些规则只是固定的验证规则而已

                 导入/导出 ,可以在vo中的字段加上该字段将是excel中的第几列,有什么格式化的规则等等

                 aop:使用特定的主键可以作为一个拦截标志,然后配合注解中的固定信息给出拦截器处理的动作功能,

                           如计算方法的执行时间,方法的输入参数打印,事务管理等

 

二.使用方法

       2.1 定义

            注解是一个接口,使用如下的方式进行这个接口的定义

                public @interface 注解名称

           例如  public @interface FieldInfo


          2.2注解的使用范围

          可以使用  元 注解来修饰我们定义的注解
          @Retention  和  @Target
          可以参考API里面  关于这两个注解的取值都有哪些.
           
         例如:
@Retention(RetentionPolicy.RUNTIME)					
@Target({ElementType.METHOD, ElementType.TYPE})					
public @interface FieldInfo {					
					
	String value() default "";				
}

           2.2.1 @Retention:修饰注解的有效期

            该注解的取值是一个RetentionPolicy的枚举
            其中的RetentionPolicy的取值有:    我们往往是要在程序运行的时候获取注解的值,因此使用  RUNTIME的时候比较多
public enum RetentionPolicy {				
				
    SOURCE,				
    CLASS,				
    RUNTIME				
}

          用@Retention(RetentionPolicy.CLASS)修饰的注解,表示注解的信息被保留在class文件(字节码文件)中当程序编译时,但不会被虚拟机读取在运行的时候
          用@Retention(RetentionPolicy.SOURCE )修饰的注解,表示注解的信息会被编译器抛弃,不会留在class文件中,注解的信息只会留在源文件中
          用@Retention(RetentionPolicy.RUNTIME )修饰的注解,表示注解的信息被保留在class文件(字节码文件)中当程序编译时, 会被虚拟机保留在运行时

          2.2.2 @Target 注解应用在哪些对象上

          该注解的取值是一个ElementType的数组  ElementType[]   
           其中的ElementType的取值有:
 
public enum ElementType {		
		
    TYPE,		
    FIELD,		
    METHOD,		
    PARAMETER,		
    CONSTRUCTOR,		
    LOCAL_VARIABLE,		
    ANNOTATION_TYPE,		
    PACKAGE		
}


          其中的取值区别:
         


         2.3 注解接口内部的成员

               注解内部的成员都是参数,参数出现的形式类似于  方法的书写格式.
               之所以称为参数那是因为使用注解的时候  都是   @注解名(XX)   XX就是注解的参数
                有一个value的特殊参数,可以有也可以没有这个参数的.
                 如果有value这个特殊参数的  @注解名(XX)  是成立的
                但是如果没有value 这个特殊的参数, @注解名(参数名=XX) 
                
              

            例如:   Retention

            其中含有value的参数,使用的时候直接进行  Retention(RetentionPolicy.XXX)即可
            也可以写成              Retention(value = RetentionPolicy.XXX)

@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.ANNOTATION_TYPE)
public @interface Retention {
    RetentionPolicy value();
}


           例如我们定义一个含有校验信息的注解 FieldInfo
           
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.FIELD)
public @interface FieldInfo {
    /**
     * 字段名称
     */
    String name() default "";
    /**
     * 标记一个字段是否是必填项目
     */
    boolean required() default false;
    /**
     * 依赖于其他项目字段条件必填
     */
    boolean dependsRequired() default false;
    /**
     * dependsRequired为true的时候,标记一个字段条件必填的依赖字段
     */
    String[] dependsField() default {};
    /**
     * dependsRequired为true的时候,条件必填时候的策略
     */
    CheckStrategyEnum checkStrategy() default CheckStrategyEnum.NULL;
    /**
     * 是否进行长度校验
     */
    boolean lengthCheck() default false;
    /**
     * 默认字段值长度
     */
    int length() default 0;
}


          使用该注解的时候:
     
      
 @FieldInfo(name = "打款账户名中文名", required = false, dependsRequired = true, dependsField = {"currency"}, checkStrategy = CheckStrategyEnum.PRODUCT_CURRENCY_RMB)
    private String bankAccountName = null;


      2.4 注解和类的继承或接口的实现

               2.4.1 接口的实现

                     如果注解修饰了接口中的方法,那么实现类中的方法是获取不到该注解信息的

              2.4.2 父类和子类

                     同上面一样。

                     但是呢修饰在类上面的注解如果子类想获取到信息的话可以使用  @Inherited 修饰该注解

                    


        2.5 注解信息的获取

              首先呢要判定一个  被修饰的对象是否被该注解修饰
              使用  isAnnotationPresent(注解的类)
             这个方法再  Class ,Method , Field 上面都有的
              
             然后使用  getAnnotation(注解的类)  可以获取到该注解的对象
             ,然后通过该对象就可以获取到该注解里面的信息了
 
           例如上面的FieldInfo 注解
           

            

FieldInfo fdInfoAnno = null;
Field f = claz.getXXXXX ;
if (f.isAnnotationPresent(FieldInfo.class)) {
     fdInfoAnno = f.getAnnotation(FieldInfo.class);
	 chName = fdInfoAnno.name();
	 boolean required = fdInfoAnno.required();
	 ...
}


         class和method上面注解的获取是一样的。


如果注解是修饰在接口中的方法,实现类的如何获取呢?

Class<?>[] interfaces = bean.getClass().getInterfaces();

获取到接口的类,然后将这些类再按照上面的获取方法  可以得到




  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值