Java 实现可关闭或自动关闭

Java 实现可关闭或自动关闭,java,java-io,Java,Java Io,我正在学习Java,对于实现可关闭的和实现可自动关闭的接口,我找不到任何好的解释 当我实现一个接口Closeable时,我的Eclipse IDE创建了一个方法public void close()抛出IOException 我可以使用pw.close()关闭流没有接口。但是,我无法理解如何使用接口实现close()方法。这个接口的目的是什么 我还想知道:如何检查IOstream是否真的关闭了 我在使用下面的基本代码 import java.io.*; public class IOtest

我正在学习Java,对于
实现可关闭的
实现可自动关闭的
接口,我找不到任何好的解释

当我实现一个
接口Closeable
时,我的Eclipse IDE创建了一个方法
public void close()抛出IOException

我可以使用
pw.close()关闭流没有接口。但是,我无法理解如何使用接口实现
close()
方法。这个接口的目的是什么

我还想知道:如何检查
IOstream
是否真的关闭了

我在使用下面的基本代码

import java.io.*;

public class IOtest implements AutoCloseable {

public static void main(String[] args) throws IOException  {

    File file = new File("C:\\test.txt");
    PrintWriter pw = new PrintWriter(file);

    System.out.println("file has been created");

    pw.println("file has been created");

}

@Override
public void close() throws IOException {


}
(在Java 7中引入)使使用习惯用法成为可能:

现在你可以说:

try (MyResource res = new MyResource()) {
    // use resource here
}
JVM将自动为您调用
close()

是一个较旧的接口。出于某种原因,为了保持向后兼容性,语言设计者决定创建一个单独的向后兼容性。这不仅允许在try with resources中使用所有
可关闭的
类(如抛出
IOException
的流),还允许从
close()
抛出更多常规检查异常


如果有疑问,请使用
自动关闭
,您的类用户将不胜感激。

在我看来,您对接口不是很熟悉。在您发布的代码中,您不需要实现

您只需要(或应该)实现或即将实现自己的
PrintWriter
,它处理需要关闭的文件或任何其他资源

在您的实现中,调用
pw.close()
就足够了。您应该在finally块中执行此操作:

PrintWriter pw = null;
try {
   File file = new File("C:\\test.txt");
   pw = new PrintWriter(file);
} catch (IOException e) {
   System.out.println("bad things happen");
} finally {
   if (pw != null) {
      try {
         pw.close();
      } catch (IOException e) {
      }
   }
}
上面的代码与Java6相关。在Java 7中,这可以更优雅地完成(请参见)。

,并且专门用于IO流:它抛出
IOException
,而不是
Exception
,并且是幂等的,而
AutoCloseable
不提供这种保证

这在两个接口的javadoc中都有解释

实现
AutoCloseable
(或
Closeable
)允许将类用作Java 7中引入的构造的资源,这允许在块末尾自动关闭此类资源,而无需添加明确关闭资源的
最终


您的类并不表示可关闭的资源,实现此接口绝对没有意义:无法关闭
IOTest
。它甚至不可能实例化它,因为它没有任何实例方法。记住,实现接口意味着类和接口之间存在is-a关系。这里没有这种关系。

这里是一个小例子

public class TryWithResource {

    public static void main(String[] args) {
        try (TestMe r = new TestMe()) {
            r.generalTest();
        } catch(Exception e) {
            System.out.println("From Exception Block");
        } finally {
            System.out.println("From Final Block");
        }
    }
}



public class TestMe implements AutoCloseable {

    @Override
    public void close() throws Exception {
        System.out.println(" From Close -  AutoCloseable  ");
    }

    public void generalTest() {
        System.out.println(" GeneralTest ");
    }
}
以下是输出:

GeneralTest 
From Close -  AutoCloseable  
From Final Block

try with resources
语句


try with resources语句是声明一个或多个资源的
try
语句。
资源
是一个必须在程序完成后关闭的对象。
try with resources语句
确保在语句末尾关闭每个资源。任何实现
java.lang.AutoCloseable
的对象(包括实现
java.io.Closeable
的所有对象)都可以用作资源

下面的示例从文件中读取第一行。它使用
BufferedReader
的实例从文件中读取数据
BufferedReader
是程序完成后必须关闭的资源:

static String readFirstLineFromFile(String path) throws IOException {
    try (BufferedReader br =
                   new BufferedReader(new FileReader(path))) {
        return br.readLine();
    }
}
在本例中,try with resources语句中声明的资源是BufferedReader。声明语句出现在try关键字后面的括号内。JavaSE7及更高版本中的类
BufferedReader
实现了接口
Java.lang.AutoCloseable
。由于
BufferedReader
实例是在try with resource语句中声明的,因此无论try语句是正常完成还是突然完成(由于方法
BufferedReader.readLine
引发
IOException
),它都将关闭

在JavaSE7之前,您可以使用
finally
块来确保资源关闭,而不管try语句是正常完成还是突然完成。以下示例使用
finally
块而不是
try with resources
语句:

static String readFirstLineFromFileWithFinallyBlock(String path)
                                                     throws IOException {
    BufferedReader br = new BufferedReader(new FileReader(path));
    try {
        return br.readLine();
    } finally {
        if (br != null) br.close();
    }

}

请。

最近我读了一本JavaSE8程序员指南ii

我发现了
AutoCloseable
Closeable
之间的区别

Java 7中引入了
AutoCloseable
接口。在此之前,另一个接口 已存在的被称为可关闭的
。这与语言设计者想要的相似,具有 下列例外情况:

  • Closeable
    将引发的异常类型限制为
    IOException
  • Closeable
    要求实现是幂等的
语言设计者强调向后兼容性。自从改变了现有的 接口不受欢迎,他们制作了一个名为
AutoCloseable
的新接口。这个新的 接口没有
可关闭的
严格。因为
可关闭
符合
AutoCloseable
,它在引入后者时开始实现
AutoCloseable

原因很简单:
Closeable.close()
抛出
IOException
。许多有利于try with resources的
close()
方法会抛出其他已检查的异常(例如
java.sql.Connection.close()
so
AutoCloseable.close()
抛出
Exception
。更改现有的
Closeable
契约
static String readFirstLineFromFileWithFinallyBlock(String path)
                                                     throws IOException {
    BufferedReader br = new BufferedReader(new FileReader(path));
    try {
        return br.readLine();
    } finally {
        if (br != null) br.close();
    }

}