java反射

java反射相关类

class类

正在运行在内存中的所有类都是该类的实例对象,每个class类都包含本类的所有信息

类内部的主要信息

  • Field;所有属性
  • Method:所有方法
  • Constructor:所有构造方法

Field类

通过反射的class类可以得到一个Field对象时,其中包含了某一个类其中一个属性的所有信息

类内部主要信息

  • 标注在属性上的注解
  • 属性名
  • 属性的数据类型
  • 属性的访问修饰符

Constructor类

描述Class类中的构造方法的一个类

类内部的主要信息

  • 构造方法的访问修饰符

  • 构造方法的参数

    • 参数的数据类型
    • 参数名字
    • 标注在参数上的注解

method类

描述clsass类中所有方法(不包括构造方法的类),包括抽象方法

类内部的主要信息

  • Constructor类内部主要信息相同
  • 方法的返回类型

Class类内部主要信息

Field类(变量)

  • 包括public和非public修饰的变量,请可以获取继承下来的变量

  • 获取不了父类被protect修饰的变量

  • Field类常用方法

    • Field[] getFields():获取类中所有被public修饰的所有变量
    • Field getField(String name):根据变量名获取类中的一个变量,该变量必须被public修饰
    • Field getDeclaredField(String name):根据姓名获取类中的某个变量,无法获取继承下来的变量
    • Field[] getDeclaredFields():获取类中所有的变量,但无法获取继承下来的变量

Constructor类(构造器)

  • 包括公有的和私有的构造器

  • 可以通过强吻(setAccessible())方法强制访问的构造器,实例化对象,这个是破坏单例模式的途径

  • Constructor类常用方法

    • Constuctor[] getConstructors():获取类中所有被public修饰的构造器
    • Constructor getConstructor(Class…<?> paramTypes):根据参数类型获取类中某个构造器,该构造器必须被public修饰
    • Constructor[] getDeclaredConstructors():获取类中所有构造器
    • Constructor getDeclaredConstructor(class…<?> paramTypes):根据参数类型获取对应的构造器

Declared修饰相关说明

  • 有Declared修饰的方法:可以获取该类内部包含的所有变量、方法和构造器,但是无法获取继承下来的信息
  • 无Declared修饰的方法:可以获取该类中public修饰的变量、方法和构造器,可获取继承下来的信息

Method类(普通方法)

  • 包括共有的和私有的修饰方法,且可以继承下来的方法

  • 无法获取父类被protect修饰符修饰的方法

  • Method类常用方法

    • Method[] getMethods():获取类中被public修饰的所有方法
    • Method getMethod(String name, Class…<?> paramTypes):根据名字和参数类型获取对应方法,该方法必须被public修饰
    • Method[] getDeclaredMethods():获取所有方法,但无法获取继承下来的方法
    • Method getDeclaredMethod(String name, Class…<?> paramTypes):根据名字和参数类型获取对应方法,无法获取继承下来的方法

注解(Annotation)

  • 反射常用方法

    • Annotation[] getAnnotations():获取该对象上的所有注解
    • Annotation getAnnotation(Class annotaionClass):传入注解类型,获取该对象上的特定一个注解
    • Annotation[] getDeclaredAnnotations():获取该对象上的显式标注的所有注解,无法获取继承下来的注解
    • Annotation getDeclaredAnnotation(Class annotationClass):根据注解类型,获取该对象上的特定一个注解,无法获取继承下来的注解
  • 只有注解的@Retension标注为RUNTIME时,才能够通过反射获取到该注解,@Retension 有3种保存策略

    • SOURCE:只在**源文件(.java)**中保存,即该注解只会保留在源文件中,编译时编译器会忽略该注解,例如 @Override 注解
    • CLASS:保存在字节码文件(.class)中,注解会随着编译跟随字节码文件中,但是运行时不会对该注解进行解析
    • RUNTIME:一直保存到运行时,用得最多的一种保存策略,在运行时可以获取到该注解的所有信息

反射的应用场景(常见的)

Spring 实例化对象:当程序启动时,Spring 会读取配置文件applicationContext.xml并解析出里面所有的 标签实例化到IOC容器中。

反射 + 工厂模式:通过反射消除工厂中的多个分支,如果需要生产新的类,无需关注工厂类,工厂类可以应对各种新增的类,反射可以使得程序更加健壮。

JDBC连接数据库:使用JDBC连接数据库时,指定连接数据库的驱动类时用到反射加载驱动类

比较一个对象前后数据的异同可以使用反射

反射的优势及缺陷

优点

  • 增加程序的灵活性:面对需求变更时,可以灵活地实例化不同对象

缺陷

  • 破坏类的封装性:可以强制访问 private 修饰的信息
  • 反射相比直接实例化对象、调用方法、访问变量,中间需要非常多的检查步骤和解析步骤,JVM无法对它们优化。(使用反射会产生比较多的临时对象,导致GC频繁)
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值