1.自定义类加载器
继承ClassLoader,重写findClass()方法
package com.wpao.classloader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;//自定义类加载器,用于加载特定路径下的class文件
public class MyClassLoader extends ClassLoader{
private String url;//class文件的路径,类加载器用于加载特定路径下的class文件
private String name;//类加载器的名字
public MyClassLoader(ClassLoader parent,String url, String name) {
super(parent);//使用指定的 父类加载器
this.url = url;
this.name = name;
}public MyClassLoader(String url,String name) {
super();//使用系统默认的加载器作为该加载器的父类
this.url = url;
this.name = name;
}
//读取class文件为二进制的字节输入流,并转化为Class对象
@Override
protected Class<?> findClass(String name) throws ClassNotFoundException {
byte[] date = readClassToBytes(name);//将文件通过输入流转化为字符数组
Class<?> c = defineClass(name, date, 0, date.length);//调用ClassLoader的defindClass方法,转化字符数组为对应的Class实例
return c;
}
//读取Class文件生成字节数组
private byte[] readClassToBytes(String name){
name = name.replaceAll("\\.", "/");
String fileName = url + name + ".class";
FileInputStream is = null;
byte[] date = null;
try {
File file = new File(fileName);
is = new FileInputStream(file);//输入流
int length = is.available();
date = new byte[length];
is.read(date);//输入流读入字符数组中
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally{
if(is != null){
try {
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
return date;
}
@Override
public String toString() {
return name;//当前类加载器的名字
}
}
2.测试类
package com.wpao.classloader;
public class Demo {
private static String date = "Demo";
public Demo() {
System.out.println("构造方法:"+date+" "+this.getClass().getClassLoader());
}
}
3.main测试
通过调用loadClass()方法去加载类,而非使用findClass()方法
public class MyTest {
public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException {
//测试,非当前classpath下的Demo类的加载,该父类加载器为AppClassLoader
MyClassLoader c1 = new MyClassLoader("D:/test/","父类加载器为AppClassLoader的类加载器");
Class<?> cl1 = c1.loadClass("com.wpao.classloader.Demo");
cl1.newInstance();//相当于调用其构造方法,开始进行加载
//测试,非当前classpath下的Demo类的加载,该父类加载器为null即BootStrapClassLoader
MyClassLoader c4 = new MyClassLoader(null,"D:/test/","父类加载器为null的类加载器");
Class<?> cl4 = c4.loadClass("com.wpao.classloader.Demo");
cl4.newInstance();
MyClassLoader c3 = new MyClassLoader(c1,"D:/test/","父类加载器为自定义的类加载器");
Class<?> cl3 = c3.loadClass("com.wpao.classloader.Demo");
cl3.newInstance();
}
}