我有一个 Java 类,它使用自定义类加载器动态重新加载 groovy 类,我看到一些奇怪的行为,一些类没有被收集,但随着时间的推移它不会泄漏内存(例如 perm gen 不会继续无限增长)。
在我的 java 代码中,我正在加载这样的类(为简单起见,删除了样板文件):
Class clazz = groovyClassLoader.loadClass(className, true, false, true);
instance = clazz.newInstance();
然后我通过清除类加载器缓存、元注册表等动态地重新加载 groovy 类:
for (Class c : groovyClassLoader.getLoadedClasses()){
GroovySystem.getMetaClassRegistry().removeMetaClass(c);
}
groovyClassLoader.clearCache();
现在,如果我只是循环这段代码,不断加载然后重新加载我的 groovy 类,我会看到奇怪的行为(我的测试代码实际上只是在循环重新加载过程 - 它对创建的任何对象等都没有做任何事情,所以上面代码中的实例只是本地的,所以应该对 GC 有好处)。
如果我运行它,将 maxpermsize 设置为 128m 然后我得到泄漏行为并且它 OOM permgen 错误:
但是,如果我再次运行它并将 maxpermsize 增加到 256m,那么一切都很好,它可以永远运行(这个图像是 1 小时,但我已经运行了整晚,做了数千次重新加载):
有没有人遇到过类似的行为?或有什么想法?同样奇怪的是,在第一个示例中,内存使用量是逐步增加而不是稳定增加。