首先是类的加载,连接,初始化
四种获取类的Class对象的方法
1、类型名.class说明:
基本数据类型和void,只能通过这种方式。
2、对象.getClass():获取对象的运行时类型说明:只能用于引用数据类型
3、Class.forName(“类的全名称")类的全名称:包.类名
4、类加载器对象.loadClass(“类的全名称")
然后是四种类加载器
1、引导类加载器(Bootstrap Classloader):又称为根类加载器它负责加载]ava的核心库
它用原生代码(C/C++)来实现的,并不继承自java.lang.ClassLoder
2、扩展类加载器(Extension ClassLoader) JAVA_HOME/ire/ext/*.jar
3、应用程序类加载器(Application Classloader) classpath下,就是自定义类型
4、自定义类加载器例如:tomcat
Java的类加载的过程是一个双亲(parent)委托模式加载的:
当“应用程序类加载器”接到一个加载任务时:
(1)先搜索内存中是否已经加载过了,如果加载过了,就可以找到对应的Class对象,那么就不加载了。
(2)如果没有找到,把这个任务先提交给“parent”,父加载器接到任务时,也是重复(1)(2)
(3)直到传给了根加载器,如果根加载器可以加载,就完成了,如果不能加载,往回传,依次每个加载器尝试在自己负责的路径下搜索,如果找到就直接返回C1ass对象,如果一直回传到“应用程序类加载器”,还是没有找到,就会报ClassNotFoundException。
类加载器的作用:
1、最主要的作用:加载类
2、辅助的作用:可以用它来加载“类路径下”的资源文件
JavaSE:例如:bin中SrC下文件-->bin目录下
ClassLoader:
(1)静态方法
ClassLoader.getSystemResourceAsStream("src1.properties")
但是这个适用于JavaSE阶段,因为它用应用程序类加载器去加载的如果是Web阶段,用这个方法是有问题的,因为web阶段的类路径在WEB-INF/classes下,必须由它自定义类加载器
(2)非静态方法
类加载器对象.getResourceAsStream("src1.properties") Web阶段用这个
Properties:Properties类表示了一个持久的属性集。Properties可保存在流中或从流中加载。属性列表中每个键及其对应值都是字符串
通过反射查看类的信息
在运行期间,动态的获取某个类的详细信息步骤:
1、获取某个类型的Class对象
2、使用Class和java.lang.reflect包下面的其他类型的API
使用反射生成并操作对象
在运行期间,动态的创建任意类型的对象,
1、Class对象.newInstance()
前提:这个类型必须有无参构造
步骤:
(1)获取Class对象
(2)直接调用Class对象.newInstance()
2、构造器来创建对象
步骤:
(1)获取Class对象
(2)获取构造器对象,获取其中一个
C1ass类中有这样的方法:
Constructor getDeclaredConstructor(Class<?>..…parameterTypes)
parameterTypes:构造器形参的类型列表
(3)用构造器创建对到 java.lang.reflect.Constructor类型中:
T newInstance(Object...initargs)
initargs:创建对象时,给构造器的实参列表
运行期间,动态的为对象的属性赋值或获取属性值步骤:
1、获取Class对象
2、获取Field属性对象
3、创建实例对象,Class代表的类型的实例对象
4、调用Fie1d对象.set(实例对象,属性值)调用Field对象.get(实例对象)
说明:如果属性是私有的,那么可以调用Field对象.setAccessible(true);
在运行期间,动态的调用任意对象的任意方法步骤:
1、获取Class对象
2、获取Method对象
方法有重载,就用方法名+形参列表clazz.getDeclaredMethod(name,parameterTypes)
3、创建实例对象
4、调用方法
public static Object createobject() {
try {
// 创建properties集合
Properties pro = new Properties();
// 从文件中加载内容到集合中
pro.load(BeanDemo.class.getResourceAsStream("/stu.properties"));
// 从集合中获得类名
String className = pro.getProperty("class");
// 通过反射获得Class对象
Class c = Class.forName(className);
// 快速创建对象
Object obj = c.newInstance();
// 遍历集合
Set names = pro.stringPropertyNames();
for (String name : names) {
// 判断name是否class
if (name.equals("class"))
continue;
// 获得值
String value = pro.getProperty(name);
// name:成员变量名
// 根据成员变量名获得对应的Field对象
Field f = c.getDeclaredField(name);
// 强制反射
f.setAccessible(true);
// 获得成员变量的类型
Class typeclass = f.getType();
if (typeclass == int.class) {// 判断成员变量的数据类型是否是int类型
f.setInt(obj, Integer.parseInt(value));
} else {
// 给对象的赋值
f.set(obj, value);
}
}
// 返回对象
return obj;
} catch (Exception e) {
throw new RuntimeException(e);
}
}