Class类
- Class类也是类的一种,只是名字和class关键字高度相似。Java是大小写敏感的语言。
- Class类的对象内容是你创建的类的类型信息,比如你创建一个shapes类,那么,Java会生成一个内容是shapes的Class类的对象
- Class类的对象不能像普通类一样,以 new shapes() 的方式创建,它的对象只能由JVM创建,因为这个类没有public构造函数
Class类的作用是运行时提供或获得某个对象的类型信息,和C++中的typeid()函数类似。这些信息也可用于反射。
在面向对象的世界里,万事万物皆对象。(java语言中,静态的成员、普通数据类型除外)。那么,类是不是对象呢?类是谁的对象呢?
答: 类是对象,类是java.lang.Class类的实例对象首先,我们创建一个类
//依照万事万物皆对象的原则,该类是一个对象
class Happy{
}
接着创建该对象的一个实例:
Happy happy = new Happy();
//Happy 这个类本身也是一个实例对象,是Class类的实例对象,如何表示这个实例对象呢
//Class类是私有的,不能直接在外部创建Class类的实例对象,只有java的虚拟机才能创建Class类的实例对象,如何表示Class类的实例对象?
//任何一个类都是Class类的实例对象,这个实例对象有三种表示方式
下面c1、c2、c3 分别是类类型的三种表达方式
// 第一种--->任何一个类都有一个隐含的静态成员变量class
Class c1 = Happy.class;
// 第二种,已知该类的对象,通过getClass()方法
Class c2 = happy.getClass();
// c1,c2表示了Happy 类的类类型(class type),一个类只能是Class的一个实例对象
// 结果: c1=c2
Class c3 = null;
try {
// 第三种
c3 = Class.forName("com.chao.happy.Happy");
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
// 结果 :c2=c3
当然,我们还可以通过类类型创建类的对象实例:
//需要有无参数的构造方法
Happy Happy2 =(Happy )c1.newInstance();
注意: Class.forName(“类的全称”) 这个方法不仅表示了,类的类类型,还代表了动态加载类。请大家区分编译、运行编译时刻加载类是静态加载类、运行时刻加载类是动态加载类
Class类的基本API操作
//要获取类的信息 首先要获取类的类类型
Class c = obj.getClass();
//获取类的名称
c.getName()
/*
* Method类,方法对象
* 一个成员方法就是一个Method对象
*/
//法获取的是所有的public的函数,包括父类继承而来的
Method[] ms = c.getMethods();
//获取的是所有该类自己声明的方法,不问访问权限
Method[] ms = c.getDeclaredMethods();
//得到方法的返回值类型的类类型
Class returnType = ms[i].getReturnType();
//得到方法的名称
c.getMethods()[i].getName();
//获取参数类型--->得到的是参数列表的类型的类类型
Class[] paramTypes = c.getMethods()[i].getParameterTypes();
/*
* Field类封装了关于成员变量的操作
* java.lang.reflect.Field
* 成员变量也是对象
*/
//获取的是所有的public的成员变量的信息
Field[] fs = c.getFields();
//获取的是该类自己声明的成员变量的信息
Field[] fs = c.getDeclaredFields();
//得到成员变量的类型的类类型
Class fieldType = c.getDeclaredFields()[i].getType();
String typeName = fieldType.getName();
//得到成员变量的名称
String fieldName = c.getDeclaredFields()[i].getName();
/*
* 构造函数也是对象
* java.lang. Constructor中封装了构造函数的信息
*/
// 获取所有的public的构造函数
Constructor[] cs = c.getConstructors();
// 得到所有的构造函数
Constructor[] cs = c.getDeclaredConstructors();
c.getDeclaredConstructors()[i].getName();
//获取构造函数的参数列表--->得到的是参数列表的类类型
Class[] paramTypes = c.getDeclaredConstructors()[i].getParameterTypes();
方法的反射
- 如何获取某个方法
方法的名称和方法的参数列表才能唯一决定某个方法
Method m = c.getMethod(“print”, int.class,int.class); - 方法反射的操作
method.invoke(对象,参数列表) - 为什么要用方法的反射
增加程序的灵活性 - 通过Class,Method来认识泛型的本质
java中的泛型是防止错误输入,编译之后就不存在泛型了。