Class类分析
基本介绍
- Class也是类,因此也继承Object类
- Class类对象不是new出来的,而是系统创建的
- 对于某个类的Class类对象,在内存中只有一份,因为类只加载一次
- 每个类的实例都会记得自己是由哪个Class实例所生成
- 通过Class可以完整地得到一个类的完整结构,通过一系列API
- Class对象是存放在堆的
- 类的字节码二进制数据,是放在方法区的,有的地方称为类的元数据(包括方法代码、变量名、方法名、访问权限等)
简单的方法调用
package events;
import java.lang.reflect.Field;
public class Class_ {
public static void main(String[] args) throws Exception {
String classPath = "events.Cat";
Class<?> aClass = Class.forName(classPath);
System.out.println(aClass);//显示aClass是哪个类的Class对象:events.Cat
System.out.println(aClass.getClass());//显示aClass运行类型:java.lang.Class
//得到包名
System.out.println(aClass.getPackage().getName());//events
//得到类名
System.out.println(aClass.getName());//events.Cat
//通过aClass创建对象实例
Cat c = (Cat)aClass.newInstance();
System.out.println(c);//Cat.toString()
//通过反射获取属性age
Field age = aClass.getField("age");
System.out.println(age.get(c));//默认值 0,私有属性会报错
//通过反射给属性设值
age.set(c, 3);
System.out.println(age.get(c));//3
//遍历得到所有属性
Field[] fields = aClass.getFields();
for(Field f: fields){
System.out.println(f.getName());
}
//输出age、name、isCat
}
}
获取Class对象的6种方法
- Class.forName():代码阶段/编译阶段
- 类.class:加载阶段
- 作用:多用于参数传递,比如通过反射得到对应构造器对象
- 对象.getClass():运行阶段
- 类加载器得到Class对象
- 基本类型
- 基本类型的包装类
- 例子:
package events;
import java.lang.reflect.Field;
public class Class_ {
public static void main(String[] args) throws Exception {
//1、编译阶段 forName
String classPath = "events.Cat";
Class<?> cls1 = Class.forName(classPath);
System.out.println(cls1);//class events.Cat
//2、类加载阶段 类.class
Class cls2 = Cat.class;
System.out.println(cls2);//class events.Cat
//3、对象.getClass() 运行类型,即这个对象对应的Class对应的类
Cat cat = new Cat();
Class cls3 = cat.getClass();
System.out.println(cls3);//class events.Cat
System.out.println(cls3.getClass());//class java.lang.Class
//4、4种类加载器获取类的Class对象
//先得到类加载器
ClassLoader classLoader = cat.getClass().getClassLoader();
//通过类加载器得到Class对象
Class<?> cls4 = classLoader.loadClass(classPath);
System.out.println(cls4);//class events.Cat
//5、基本类型
Class<Integer> integerClass = int.class;
Class<Character> characterClass = char.class;
Class<Boolean> booleanClass = boolean.class;
System.out.println(integerClass);//int
System.out.println(characterClass);//char
System.out.println(booleanClass);//boolean
//6、基本类型对应的包装类,可以通过type得到Class对象
Class<Integer> type = Integer.TYPE;
Class<Character> type1 = Character.TYPE;
System.out.println(type);//int
System.out.println(type1);//char
//一个类只有一个Class对象,该类不同实例得到的Class对象哈希值都一样
}
}
哪些类型有Class对象(都可以使用.class得到)
- 外部类,成员内部类,静态内部类,局部内部类,匿名内部类
- interface
- 数组
- enum
- annotation
- 基本数据类型
- void