【问题标题】:Should I close a stream which I did not create?我应该关闭不是我创建的流吗?
【发布时间】:2017-10-26 12:01:19
【问题描述】:

如果我有流(InputStream 或 OutputStream),但不是我创建的,而是作为参数传递给我的方法的,我应该关闭该流吗?这是一个例子:

void method(InputStream in) {
    try {
    //Do something
    }
    finally {
        if(in != null) { 
        in.close();    //Is this needed and correct?
    }    
}

【问题讨论】:

  • 不,你不应该。
  • 无论是否关闭资源,都应该在方法 JavaDoc 注释 中声明。
  • @sdm 我可能是错的,但如果你写了method,你就会有一些背景知识,其中InputStream 将被传递给你的方法以便能够正确使用在你的方法中?如果您不知道如何调用您的方法,考虑到流也会在其他地方使用,它是否容易产生副作用?

标签: java inputstream outputstream


【解决方案1】:

通常不建议关闭与该类无关的流。

原因如下,

  1. 传递给该方法的流可以在其他地方使用。 可重用流在 java 中可用。如果流关闭它 无法重新打开和重复使用。
  2. 如果关闭流时出现异常,您不知道如何处理 处理那个。因为您正在处理一般输入流并且它 可能来自文件、网络等任何地方。

类打开流负责关闭它。

【讨论】:

    【解决方案2】:

    真的,“这取决于”。

    作为一般规则,您不应关闭您没有责任打开的流,但要给出正确答案,我们必须了解上下文。

    责任委派很可能要求您的方法消费并关闭流 - 如果是这种情况,那么它应该在代码中明确。

    如果您的方法名为readFromStreamAndClose(InputStream in),那么您的方法关闭流这一事实非常明显。

    在您自己打开流的情况下,您始终可以使用try-with-resources 块来为您关闭流 - 在与创建流相同的抽象级别。在这种情况下 - 您的方法(在比打开流时更低的级别调用)不应关闭流。

    【讨论】:

    • 我同意如果 API 文档确实说应该关闭传递给它的流,那么作为实现者我必须关闭它以符合 API。这就是为什么我有这个问题的原因,因为在编写实现时,被强制关闭我没有创建的流感觉很奇怪,我可以想到以后可能需要这个流的场景。
    • 大多数情况下你是正确的 sdm。鉴于在这种情况下强制执行该行为 - 请通过文档明确说明。
    【解决方案3】:

    我不认为 JVM 规范对此做出任何保证。你真的应该最终关闭这些资源。

    当进程结束时,操作系统将释放与其相关的所有资源(包括内存、文件句柄和网络套接字)。

    有操作系统工具可以检查打开的文件和流

    【讨论】:

      【解决方案4】:

      不,您不必这样做,因为它可能会在代码的其他地方使用。

      【讨论】:

        【解决方案5】:

        您确实记录了该方法:“关闭流”并将方法名称更改为类似于 readAndClose。

        或者创建一个参数boolean closeStream,如果为真则关闭。

        此外,如果流不支持标记/搜索/重置,则没有理由将其保持打开状态。

        【讨论】:

        • closes记录方法。否则,它看起来像是对调用者的指示。
        • "创建一个参数 boolean closeStream 并在 true 时关闭。"最好不要这样做,因为该参数的含义不明确:您可能会将其与其他方法混淆,并认为“true”意味着“保持流打开”。如果您要使用参数,则两个元素的枚举 enum Blah { KEEP_OPEN, CLOSE } 会更好,因为它可以自我记录含义。
        • 在任何情况下它都可以关闭你需要记录它的流
        • 是的,但是告诉某人做某事和说你会做之间有很大的区别。对 1 个字符吹毛求疵似乎是在吹毛求疵,但它大大改变了意思。
        • 哦.. 谢谢指出,我确实喜欢使用枚举的解决方案
        猜你喜欢
        • 2015-03-18
        • 1970-01-01
        • 2019-07-20
        • 1970-01-01
        • 1970-01-01
        • 2010-09-06
        • 2010-12-22
        • 1970-01-01
        • 2013-08-05
        相关资源
        最近更新 更多