关闭DataInputStream会同时关闭FileInputStream吗?

10
FileInputStream fstream = new FileInputStream(someFile.getPath());
DataInputStream in = new DataInputStream(fstream);

如果我调用in.close(),它会同时关闭fstream吗?我的代码出现了以下GC异常:

java.lang.OutOfMemoryError: GC overhead limit exceeded

2个回答

9

是的,DataInputStream.close()方法也会关闭你的FileInputStream

这是因为DataInputStream继承了FilterInputStream,而FilterInputStream实现了close()方法:

    public void close() throws IOException {
        in.close();
    }

BufferedReader br = new BufferedReader(new InputStreamReader(in)); 缓冲读取器br = 新缓冲读取器(新输入流读取器(in)); - Adyz
如果你现在的问题是关于 BufferedReader.close() 是否会关闭 InputStreamReader,答案也是“是的 - 会”。 - Andremoniy
1
很难在这两个事实之间建立逻辑联系,但是在读取完毕后,您必须关闭 BufferedReader。 - Andremoniy
FileInputStream fstream = new FileInputStream(someFile.getPath()); DataInputStream in = new DataInputStream(fstream); BufferedReader br = new BufferedReader(new InputStreamReader(in)); // 逐行读取文件 DataInputStream.close(); // 但我没有关闭缓冲读取器.. 这可能会导致GC异常吗? - Adyz
@Ady.Q 嗯,实际上在某些情况下它是可以的。 - Andremoniy
显示剩余5条评论

6
您的 DataOutputStream 继承了其 close() 方法自 FilterOutputStream,后者的文档指出:

关闭此输出流并释放与该流相关联的任何系统资源。

FilterOutputStream 的 close 方法调用其 flush 方法,然后调用其底层输出流的 close 方法。

所有 Writer 实现都应该是如此(尽管文档中没有说明)。


为避免在使用 Java 中的 Streams 时遇到内存问题,请使用以下模式:

// Just declare the reader/streams, don't open or initialize them!
BufferedReader in = null;
try {
    // Now, initialize them:
    in = new BufferedReader(new InputStreamReader(in));
    // 
    // ... Do your work
} finally {
    // Close the Streams here!
    if (in != null){
        try {
            in.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

由于Java7引入了AutoCloseable-interface,这使得代码看起来不那么混乱,因为所有的Stream/Writer/Reader类都实现了它。请参见教程


一个关闭的Reader/Stream能否再次打开?另外,您认为这种模式可以在多线程系统中使用,其中每个线程都想访问相同的位置以读取数据吗? - Onat Korucu
据我所知,流无法重新打开。它们需要重新创建。就多线程而言,流不是线程安全的。因此,如果您需要在线程之间共享数据,请在一个线程中读取它,并通过线程安全集合共享该状态。 - Lukas Knuth

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接