这是有罪的代码:
// Demo the java.lang.OutOfMemoryError: Java heap space error.
import java.util.*;
public class Bozo {
void TstReadFile() {
SubBozo sb = new SubBozo();
sb.readFile();
}
public static void main(String[] args) {
Bozo b = new Bozo();
b.TstReadFile();
}
}
/** Read in the observing list file. */
import java.io.*;
import java.util.*;
public class SubBozo {
public boolean readFile() {
int lineCt = 0; // Count the lines read in observingList.
long heap,
heapMaxSize,
heapFreeSize;
String s = "Unstarted";
FileInputStream fis = null;
DataInputStream in = null;
BufferedReader br = null;
try {
fis = new FileInputStream("../data/observingList");
in = new DataInputStream(fis);
br = new BufferedReader(new InputStreamReader(in));
} catch (Exception e) {
System.out.println("Couldn't open ../data/observingList because " +
e.getMessage());
}
boolean go = true;
while (go) {
try {
s = br.readLine(); // Lines should not be longer than say 256 characters.
} catch (Exception e) {
System.out.println("Couldn't read ../data/observingList because " +
e.getMessage());
heap = Runtime.getRuntime().totalMemory();
heapMaxSize = Runtime.getRuntime().maxMemory();
heapFreeSize = Runtime.getRuntime().freeMemory();
System.out.println("" + lineCt + ") " + "Total Memory (MB): " +
(heap / 1048576) + "\n Heap Max Size (MB): " +
(heapMaxSize / 1048576) +
"\n Heap Free Size (MB): " +
(heapFreeSize / 1048576));
go = false;
}
if ((lineCt++ % 1000) == 0) {
System.gc();
heap = Runtime.getRuntime().totalMemory();
heapMaxSize = Runtime.getRuntime().maxMemory();
heapFreeSize = Runtime.getRuntime().freeMemory();
System.out.println("" + lineCt + ") " + "Total Memory (MB): " +
(heap / 1048576) + "\n Heap Max Size (MB): " +
(heapMaxSize / 1048576) +
"\n Heap Free Size (MB): " +
(heapFreeSize / 1048576));
}
}
try {
br.close();
in.close();
fis.close();
} catch (Exception e) {
System.out.println("Couldn't close the input file stream because " +
e.getMessage());
}
return true;
}
}
运行时,使用以下命令:
星云:finderChart/src java Bozo
它会引发内存不足错误。这是打印输出:
1) 总内存 (MB): 119 堆最大大小 (MB): 1776 堆可用大小 (MB): 118
1001) 总内存 (MB): 119 堆最大大小 (MB): 1776 堆可用大小 (MB): 119
2001) 总内存 (MB):119 堆最大大小 (MB):1776 堆可用大小 (MB):119
3001) 总内存 (MB): 119 堆最大大小 (MB): 1776 堆可用大小 (MB): 119
线程“主”java.lang.OutOfMemoryError 中的异常:java.lang.AbstractStringBuilder.expandCapacity(AbstractStringBuilder.java:100) 处 java.util.Arrays.copyOf(Arrays.java:2882) 处的 Java 堆空间。在 java.io.BufferedReader.readLine(BufferedReader.java:345) 在 java.io.BufferedReader.readLine(BufferedReader) 的 java.lang.StringBuffer.append(StringBuffer.java:306) 的 AbstractStringBuilder.append(AbstractStringBuilder.java:515) .java:362) 在 SubBozo.readFile(SubBozo.java:34) 在 Bozo.TstReadFile(Bozo.java:10) 在 Bozo.main(Bozo.java:15)
现在是奇怪的部分,但我怀疑你已经看过了。JVM 每 1000 行打印一次它的内存使用情况。它没有耗尽内存。
当错误被抛出时,它错过了捕获:
尝试 {
s = br.readLine();
} 捕捉(异常 e){
System.out.println("Couldn't read ../data/observingList because "
...
}
所以让我们尝试增加内存:java -Xmx1024m Bozo
相同的结果,所以我不会重复它。
发生的事情是正在读取的文件 obasrvingList 中有一些很长(> 2048 字节)的行。这吓坏了 Java,但直到我尝试在 Vim 中编辑文件并发现 vim 无法编辑它时,才发现对于一般的文本阅读器来说,异常长的行是一个问题。
TIA
汤姆