Java,运行时类重新加载

时间:2010-11-16 13:33:41

标签: java class reloading

我正在寻找一种在运行时将类重新加载到Java的方法。其动机是提高调试效率。该应用程序是一种典型的客户端/服务器设计,可以同步处理请求。为每个请求实例化“处理程序”对象。这是我打算动态替换的唯一类。由于每个请求都处理一个新的实例,因此重新加载此类将不会产生任何副作用。简而言之,我不希望每次更改此模块时都重新启动整个应用程序。

在我的设计中,Java进程意识到在请求之间的类路径中已经更新了.class文件。发生这种情况时,将卸载“handler”类并加载一个新类。

我知道我可以使用classLoader接口加载一个新类。我似乎无法找到正确的“卸载”方式。

3 个答案:

答案 0 :(得分:4)

如果没有对它们的剩余引用,将像任何其他对象一样卸载和垃圾收集。这意味着必须没有可访问的类实例(由该特定的类加载器实例加载),并且类加载器实例本身也必须符合垃圾回收的条件。

基本上,您所要做的就是创建一个新的类加载器实例来加载该类的新版本,并确保不会引用旧版本的实例。

答案 1 :(得分:1)

我相信你实际上需要一个类加载器的层次结构,并且为了重新加载你实际上摆脱了低级类加载器(通过normall GC意味着),因此它加载了所有类。据我所知,Java EE应用服务器使用这种技术来重新加载应用程序,当一个类加载器中加载的框架代码想要使用在其他地方加载的类时,会有各种有趣的结果。

答案 2 :(得分:0)

截至2015年,java的类重新加载也是一个缺失的功能。

  • 使用 OSGi 创建一个类重装应用程序。
  • 使用jrebel进行测试。还有一些其他人做同样的事情。
  • 使用应用程序服务器并将要重新加载的部件外部化到单独的Web应用程序中。然后继续部署/取消部署。由于悬挂旧的ClassLoader实例,你最终会得到一些perm gen space溢出的错误。
  • 使用脚本运行器执行可更改代码的各个部分。 JSR-223 Java Scripting API支持脚本语言“Java”。

我写了一个关于类重新加载的系列文章。但所有这些方法都不适合生产。

恕我直言,这个类重装在java中很乱,不值得尝试。但我非常希望这是java中的规范。