爬梯:注解和反射夯实

学习资源整理自:B站《狂神说》

注解 Annotation

从JDK5.0开始使用

  • 注解的作用

    • 不是程序本身,可以对程序作出解释(类似于注释,用于说明)
    • 可以被其他程序读取(编译器等)
  • 注解的格式

    • 注解以 @注解名 存在,可以带有参数
  • 一般应用场景

    • 可以附加在package、class、method、field等上,给这些元素添加额外的辅助信息,并且可以通过反射机制对这些信息进行获取

元注解

  • 元注解的作用是注解其它注解,java定义了4个标准的meta-annotation类型,他们被用来提供对其它annotation类型做说明;

  • 这些类型和它们所支持的类在java.lang.annotation包中可以找到

    • @Target:用于描述注解的适用范围(描述注解可以用在什么地方)
    • @Retention:表示需要在什么级别保存改注解信息,描述注解的生命周期
      • (SOURCE < CLASS < RUNTIME )
    • @Document:说明该注解将被包含在javadoc中
    • @Inherited:说明子类可以继承父类中的该注解,注解的继承

自定义注解

  • 使用@interface声明注解,public @interface name{}
  • 自动继承java.lang.annotation.Annotation接口
  • 其中每个方法实际声明一个配置参数,方法名就是参数名,返回值类型就是参数类型(返回值只能是基本类型,Class、String、enum)
  • 可以通过default来声明参数的默认值
  • 如果只有一个参数成员,一般命名为value
  • 注解元素必须要有值,我们定义注解元素时,经常使用空字符串 0 作为默认值。
    在这里插入图片描述

反射 Reflection

反射概述

  • 反射是java被视为动态语言的关键,反射机制允许程序在执行期接住Reflection Api获取类的任何内部信息,并能直接操作任何对象的内部属性及方法。
  • 加载完类之后,在堆内存的方法区中就产生了一个Class类型的对象,这个对象包含了完整的类的结构信息,于是通过这个对象可以看到类的结构。这个对象就像一面镜子,所以称之为反射。

可以读取到private修饰的类和方法。

java反射机制提供的功能:

  • 在运行时判断任意一个对象所属的类
  • 在运行时构造任意一个类的对象
  • 在运行时判断任意一个类所具有的成员变量和方法
  • 在运行时获取泛型信息
  • 在运行时调用任意一个对象的成员变量和方法
  • 在运行时处理注解
  • 生成动态代理

Java反射的优点:

  • 可以实现动态编译和创建对象,体现了很大的灵活性;

Java反射的缺点:

  • 对性能有影响。使用反射基本上是一种解释操作,这类操作总是慢于直接执行相同的操作。

Class类并获取Class实例

  • Class本身也是一个类
  • Class对象只能由系统创建
  • 一个加载的类在JVM中只会有一个Class实例
  • 一个Class对象对应的是一个加载到JVM中的一个.class文件
  • 通过Class可以完整的得到一个类中的所有被加载的结构
  • Class类是Reflection的根源,针对任何你想动态加载、运行的类都需要先获得相应的Class对象。

Class类常用方法

方法名说明
static Class.forName(String name)获得指定类名的Class对象
Object newInstance()调用无参构造器,创建Class对象的一个实例
getName()返回此Class对象所表示的实体(类、接口、数组类或void)的名称
Class getSuperClass()返回当前Class对象的父类的Class对象
Class[] getInterfaces()获取当前Class对象的接口的Class数组
ClassLoader getClassLoader()返回此类的类加载器
Constructor[] getConstructors()获取当前Class对象的构造器数组
Method getMothed(String name,Class …T)返回一个Method对象,此对象的形参类型为paramType
Field[] getDeclaredFields()获取当前Class对象的字段数组

获取Class类的方法:

  • 根据类名直接获取
Class clazz = Person.class;
  • 由实例获取:
Class calzz = sutdent.getClass();
  • 根据类的路径获取:
Class clazz = Class.forName("com.ssx.People");
  • 内置基本数据类型可以直接使用 .Type
  • 可以通过ClassLoader获取

全类型Class

在这里插入图片描述

类的加载与ClassLoader

当程序主动使用一个未被加载到内存中的类时,系统会通过以下三步对该类进行初始化
在这里插入图片描述

参考JVM回首会更清晰。

引导类加载器:rt.jar

在这里插入图片描述
类加载演示
在这里插入图片描述在这里插入图片描述

反射获取泛型

  • Java采用泛型擦除的机制来引入泛型,Java中的泛型仅仅是给编译器javac使用的,确保数据的安全性和免去强制类型转换问题,可是一旦编译完成所有和反省有关的类型全部擦除
  • 为了通过反射操作这些类型,Java增加了ParameterizedType、GenericArrayType、TypeVariable和WildcardType几种类型来代表不能被归类到Class类中的类型但是又和原始类型齐名的类型
  • ParameterizedType:一种参数化类型,比如:Collection
  • GenericArrayType:一种元素类型是参数化类型或者类型变量的数组类型
  • TypeVariable:是各种类型变量的公共父接口
  • WildcardType:代表一种通配符类型表达式

在这里插入图片描述

反射获取注解

Annotation annotation = clazz.getAnnotations();//获取全部注解
clazz.getAnnotation(anno.class);
annotation.value()

小结

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值