Java 加载指定位置java文件

思路

  • 读取Person.java文件
  • 编译成.class文件
  • 加载.class文件,需要自定义类加载器
  • 获取class对象,通过反射API调用Person方法

相关代码

// 根据文件路径,编译并加载
public static Class<?> compileAndLoad(String path) {
        String type = ".class";
        JavaCompiler javaCompiler = ToolProvider.getSystemJavaCompiler();
        int result = javaCompiler.run(null, null, null, path);
        if (result != 0) {
            throw new RuntimeException("编译失败");
        }
        Class resultClass = null;

        String[] split = path.split("\\.");
        String classLocation = split[0]+ type;

        // 自定义类加载器
        MyClassLoader myClassLoader = new MyClassLoader();
        try {
            resultClass = myClassLoader.findClass(classLocation);
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
        return resultClass;
}

     /**
     * 自定义类加载器
     */
    static class MyClassLoader extends ClassLoader{

        @Override
        protected Class<?> findClass(String name) throws ClassNotFoundException {
            Path path = null;
            byte[] bytes = null;
            try {
                path = Paths.get(name);
                bytes = Files.readAllBytes(path);
            } catch ( IOException e) {
                e.printStackTrace();
            }
            String[] split = name.split("/");
            String fileName = split[split.length - 1];
            String className = fileName.split("\\.")[0];
            // 调用父类
            return super.defineClass(className, bytes, 0, bytes.length);
        }
    }

// 测试
public static void main(String[] args) throws NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException, ClassNotFoundException {
        String path = "/Users/mars/codeSpace/0bat/3source_code/1jdk/upload/Person.java";
        Class<?> aClass = compileAndLoad(path);
        System.out.println(aClass.getClassLoader());
        Object o = aClass.newInstance();
        Method say = aClass.getDeclaredMethod("say",String.class);
        Object invoke = say.invoke(o, "wang");
        System.out.println(invoke.toString());

    }

// 打印结果
//reflect.demo2.LoadOutResource$MyClassLoader@457e2f02
//hello,wang
posted @ 2021-03-10 20:14  罗曼蒂克在消亡  阅读(378)  评论(0编辑  收藏  举报