http://www.ibm.com/developerworks/rational/library/05/0816_GuptaPalanki/#javaexample
代码中的作者说存在内存泄漏。
public class LeakExample {
static Vector myVector = new Vector();
static HashSet pendingRequests = new HashSet();
public void slowlyLeakingVector(int iter, int count) {
for (int i=0; i<iter; i++) {
for (int n=0; n<count; n++) {
myVector.add(Integer.toString(n+i));
}
for (int n=count-1; n>0; n--) {
// Oops, it should be n>=0
myVector.removeElementAt(n);
}
}
}
此代码如何发生内存泄漏,而以下内容没有。是什么让两者截然不同。
public void noLeak(int size) {
HashSet tmpStore = new HashSet();
for (int i=0; i<size; ++i) {
String leakingUnit = new String("Object: " + i);
tmpStore.add(leakingUnit);
}
// Though highest memory allocation happens in this
// function, but all these objects get garbage
// collected at the end of this method, so no leak.
}
答案 0 :(得分:6)
在您的第一个示例中,并非所有向量元素都被删除(如代码中的注释所示)。由于 myVector
是static
成员变量,只要应用正在运行,它就会一直存在,并且每次调用slowlyLeakingVector()
时都会随着时间的推移而增长
在第二个示例中, tmpStore
是一个局部变量,每次从noLeak()
返回后都会进行垃圾回收。
答案 1 :(得分:2)
每次运行第一个代码时,都会添加n个元素,并删除(n-1)(0处的元素不是),因此向量会缓慢存储永远不会使用的元素。由于向量是静态的,它将一直存在,直到JVM关闭,泄漏内存。
在第二个例子中,tmpStore可以在每次调用结束时进行垃圾收集,因此不会泄漏。
答案 2 :(得分:1)
这里的关键是
for (int n=count-1; n>0; n--) {
// Oops, it should be n>=0
myVector.removeElementAt(n);
}
最后一个元素永远不会被删除,因为n
在循环中永远不会0
,即removeElementAt(0)
永远不会运行。这导致元素在向量中缓慢累积。