2011-09-10 29 views
2

应用程序需要从运行时提供的jar中加载类。这些jar应该被删除,并在运行时被其他jar取代,因为看起来ClassLoader并没有释放罐子上的文件句柄。Java Classloader在Windows下不释放文件句柄

这是一个已知的问题?是否有可用的类加载器,但没有此问题?

编辑:用例不是加载相同类的不同版本,而是加载相同接口的不同实现。这些类使用应用程序必须调用的“execute”方法实现接口。所以虽然类的卸载机制在这种情况下也是有用的,但这不是主要的用例。

回答

1

在类加载器卸载之前,ClassLoader不会释放该jar。如果不创建新的类加载器,则无法加载新版本的类,因此我没有看到您希望如何工作。

也许你想要的是一个OSGi容器,比如Apache Karaf,它允许你在运行时加载/卸载库。

+0

我为我的问题添加了一个解释来澄清,这不是关于加载同一类的不同版本,但感谢您的答案无论如何:-) –

+0

如果您只想添加类,但不使用目录来做这个,Clark的建议可能会起作用。 –

3

看看这个What is the reason that setDefaultUseCaches(false) of URLConnection is eagerly called in the org.apache.catalina.core.JreMemoryLeakPreventionListener

它也许可以回答你的问题。当使用UrlConnection,并将缓存设置为true时,它不会关闭文件处理程序。

此外,它提供了一种解决方法来将缓存设置为false。

URL url = new URL("jar:file://dummy.jar!/"); 
URLConnection uConn = new URLConnection(url) { 
    @Override 
    public void connect() throws IOException {   
     // NOOP  
    } 
}; 
uConn.setDefaultUseCaches(false); 

这只需要在使用URLConnection之前在静态块中调用。

这取决于你的类加载器是如何实现的。

相关问题