我将开始使用第三方封闭源库加载一堆数据,并想检查加载多组“数据”的速度和速度。我编写了这个简单的工具来调用数据加载以计时,并使用YourKit快速查看内存使用情况并深入研究CPU时间。
我正在Windows 7上运行它,并且在没有VM参数的情况下在JDK8上使用Eclipse。
public static void main(String[] args){
long start = System.currentTimeMillis();
// There are a few more calls involved, but not much
BlackBoxDataProvider bd = new BlackBoxDataProvider("c:\\thedata");
BlackBoxData = bd.loadTheData();
System.out.println(System.currentTimeMillis() - start + "ms");
// Keep the application alive so I can have a quick look at memory usage
while(true) {
Thread.sleep(1000);
}
}
这是加载完成后的YourKit内存快照:
然后我使用YourKit来“强制”垃圾回收,并且发生了这种情况:
显然这不是现实生活中的情况,因为我被卡在主线程的main方法中,因此我的一些引用将不被清理,但是我无法弄清楚为什么内存分配会保持不变不断增加。
每次我单击“强制系统GC”时,分配都会增加。在停止增加之前,我已经达到了11.9GB。
为什么会这样?
答案 0 :(得分:0)
所有对象扫描一次后,System.gc()将返回。如果将实现finalize()方法的对象添加到队列中,以便稍后进行清理。这意味着还不能清除那些对象(不是保存它们的队列节点),即触发GC的行为可能会暂时增加内存消耗。这就是您的情况。
简而言之,并不是所有对象都可以在一个周期内清理干净。