java 自定义类加载器URLClassLoader,动态加载任意类与资源文件 类隔离

本文介绍如何使用Java自定义类加载器加载指定目录下的类文件及资源文件,并通过示例代码展示了动态加载的过程。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

java加载器就是加载class字节码或资源文件,使用自己的类加载器加载可以自定义加载任意文件目录里的类与资源文件,类被自己的类加载器加载后,在类里调用加载器(【可以看到自己是被那个加载器加载的】)加载资源classLoader.getResource,的跟目录就会变成这个类的class所在根目录,从而实现动态加载资源文件

主要有3个
Test.java main方法与自定义加载器
Handler.java 接口 ,方便加载类后,强转,调用方法
OneHandlerImpl.java 实现接口,打印加载器与加载资源文件路径,编译后的class文件测试动态加载

idea普通java项目
项目运行一次后(为了编译), 把OneHandlerImpl.class 放到其他目录(非classpath目录), 并在同级目录建立资源文件OneHandlerImpl.config,内容随便,注意看是否能够加载

由tomcat自定义加载器思考而来,可以实现自己的webapp隔离
比如配置的web.xml配置的classpath:springmvc-servlet.xml。WEB-INF下等等,扫描的包路径

URLClassLoader默认是有双亲委托的。所以刚开始在项目里运行,打印的加载器是AppClassLoader, 所以需要把编译后的OneHandlerImpl.class放到非项目的非classpath目录,测试

Test.java

import java.io.File;
import java.net.URL;
import java.net.URLClassLoader;
import java.net.URLStreamHandler;

public class Test {

    public static void main(String[] args) throws Exception{

        Class c = Test.loadClass("/Users/proj/testclass","OneHandlerImpl");

        //使用反射调用方法
//        Object obj = c.newInstance();
//        Method method = c.getMethod("doIt");
//        method.invoke(obj);

        //通过接口强转,比反射更好
        Handler handler = (Handler) c.newInstance();
        handler.doIt();

    }

    /**
     *
     * @param classesPath  字节码文件目录,包的根目录,jar包文件绝对路径
     * @param clazzStr  类全名,包括包名
     * @return
     */
    public static Class loadClass(String classesPath , String clazzStr){
        try{
            URL[] urls = new URL[1];

            urls[0] = new URL("file",null,classesPath);

            URLClassLoader loader = new URLClassLoader(urls);

            return loader.loadClass(clazzStr);
        }catch (Exception e){
            e.printStackTrace();
        }

        return null;
    }
}

Handler.java

public interface Handler {
    void doIt();
}

OneHandlerImpl.java

public class OneHandlerImpl implements Handler {
    @Override
    public void doIt() {
        System.out.println("OneHandlerImpl");
        ClassLoader classLoader = OneHandlerImpl.class.getClassLoader();
        System.out.println(classLoader);
        System.out.printf(classLoader.getResource("OneHandlerImpl.config").getFile());
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值