在java中卸载类? [英] Unloading classes in java?

查看:411
本文介绍了在java中卸载类?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个自定义类加载器,以便桌面应用程序可以动态地从我需要与之交谈的AppServer中加载类。我们这样做是因为要做这件事所需的罐子数量是荒谬的(如果我们想要运送它们)。如果我们不在运行时从AppServer库动态加载类,我们也会遇到版本问题。



现在,我遇到了一个需要与之交谈的问题两个不同的AppServer,发现根据我首先加载的类,我可能会破坏...有没有办法强制卸载类而不实际杀死JVM?



<希望这是有道理的

解决方案

可以卸载类的唯一方法是使用的类加载器是垃圾收集的。这意味着,对每个类和类加载器本身的引用需要采用渡渡鸟的方式。



你的问题的一个可能的解决方案是为每个类都有一个类加载器jar文件,以及每个AppServer的类加载器,它将类的实际加载委托给特定的Jar类加载器。这样,您可以为每个App服务器指向不同版本的jar文件。



但这并非易事。 OSGi平台努力做到这一点,因为每个bundle都有一个不同的类加载器,并且平台解决了依赖关系。也许一个好的解决方案是看看它。



如果你不想使用OSGI,一个可能的实现可能是使用一个 JarClassloader 类。



并创建一个扩展Classloader的新的MultiClassloader类。该类内部将具有JarClassloaders的数组(或List),并且在defineClass()方法中将遍历所有内部类加载器,直到找到定义或抛出NoClassDefFoundException。可以提供几种访问器方法来向类中添加新的JarClassloaders。对于MultiClassLoader,网上有几种可能的实现方式,因此您甚至可能不需要自己编写。



如果为服务器的每个连接实例化一个MultiClassloader,原则上,每个服务器都可能使用同一个类的不同版本。



我在项目中使用了MultiClassloader的想法,其中包含用户定义的类脚本必须从内存中加载和卸载,并且运行良好。


I have a custom class loader so that a desktop application can dynamically start loading classes from an AppServer I need to talk to. We did this since the amount of jars that are required to do this are ridiculous (if we wanted to ship them). We also have version problems if we don't load the classes dynamically at run time from the AppServer library.

Now, I just hit a problem where I need to talk to two different AppServers and found that depending on whose classes I load first I might break badly... Is there any way to force the unloading of the class without actually killing the JVM?

Hope this makes sense

解决方案

The only way that a Class can be unloaded is if the Classloader used is garbage collected. This means, references to every single class and to the classloader itself need to go the way of the dodo.

One possible solution to your problem is to have a Classloader for every jar file, and a Classloader for each of the AppServers that delegates the actual loading of classes to specific Jar classloaders. That way, you can point to different versions of the jar file for every App server.

This is not trivial, though. The OSGi platform strives to do just this, as each bundle has a different classloader and dependencies are resolved by the platform. Maybe a good solution would be to take a look at it.

If you don't want to use OSGI, one possible implementation could be to use one instance of JarClassloader class for every JAR file.

And create a new, MultiClassloader class that extends Classloader. This class internally would have an array (or List) of JarClassloaders, and in the defineClass() method would iterate through all the internal classloaders until a definition can be found, or a NoClassDefFoundException is thrown. A couple of accessor methods can be provided to add new JarClassloaders to the class. There is several possible implementations on the net for a MultiClassLoader, so you might not even need to write your own.

If you instanciate a MultiClassloader for every connection to the server, in principle it is possible that every server uses a different version of the same class.

I've used the MultiClassloader idea in a project, where classes that contained user-defined scripts had to be loaded and unloaded from memory and it worked quite well.

这篇关于在java中卸载类?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆