概述
运行时类型信息(RTTI)使得你可以在程序运行时发现和使用类型信息。
它是你只能在编译期执行面向类型的操作的禁锢中解脱出来,并且可以使用某些非常强调的功能。对RTTI的需要,揭示了面向对象设计中许多有趣(并且复杂)的问题,同时也提出了如何组织程序的问题。
本章将讨论Java是如何让我们在运行时识别对象和类的信息的。主要有两种方式:一种是“传统的”RTTI,它假定我们在编译时已经知道了所有的类型;另一种是“反射”机制,它允许我们在运行时发现和使用类的信息。
类型转换前先做检查
使用类字面常量
xxx.class就是类字面量,通过 xxx instanceof xxx.class判断xxx是否是某个类的对象。
动态的Class.isInstance
Class.isInstance方法提供了一种动态地测试对象的途径。于是所有那些单调的instanceof语句就可以删除了。
示例:
public class ClassInfo {
static class Pet extends ClassInfo {
}
static class Dog extends ClassInfo {
}
static class Cat extends ClassInfo {
}
public static void main(String[] args) {
List<ClassInfo> list = new ArrayList<>();
list.add(new ClassInfo());
list.add(new Dog());
list.add(new Cat());
list.forEach(item -> {
if(Dog.class.isInstance(item)) {
System.out.println("dog class, className:" + item.getClass().getName());
} else {
System.out.println("no dog class, className:" + item.getClass().getName());
}
});
}
}
打印如下:
no dog class, className:com.study.practice.controller.ClassInfo
dog class, className:com.study.practice.controller.ClassInfo$Dog
no dog class, className:com.study.practice.controller.ClassInfo$Cat
Class.isAssignableFrom
使用Class.isAssignableFrom()来执行运行时的检查,已校验你传递的对象确实属于我们感兴趣的继承结构。
反射:运行时的类信息
如果不知道某个对象的确切类型,RTTI可以告诉你。但是有一个限制:这个类型在编译时必须已知,这样才能使用RTTI识别它,并利用这些信息做一些有用的事。换句话说,在编译时,编译器必须知道所以要通过RTTI来处理的类。
人们想要在运行时获取类的信息的另一个动机,便是希望提供在跨网络的远程平台上创建和运行对象的能力。这被称为远程方法调用(RMI),它运行一个Java程序将对象分布到多台机器上。
Class类与java.lang.reflect类库一起对反射的概念进行了支持,该类库包含了Field,Method以及Constructor类(每个类都实现了Member接口)。
动态代理
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
文章由极客之音整理,本文链接:https://www.bmabk.com/index.php/post/100155.html